r11829: remove unused #if 1
[metze/samba/wip.git] / source4 / torture / nbt / winsreplication.c
1 /* 
2    Unix SMB/CIFS implementation.
3
4    WINS replication testing
5
6    Copyright (C) Andrew Tridgell        2005
7    Copyright (C) Stefan Metzmacher      2005
8    
9    This program is free software; you can redistribute it and/or modify
10    it under the terms of the GNU General Public License as published by
11    the Free Software Foundation; either version 2 of the License, or
12    (at your option) any later version.
13    
14    This program is distributed in the hope that it will be useful,
15    but WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License for more details.
18    
19    You should have received a copy of the GNU General Public License
20    along with this program; if not, write to the Free Software
21    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 */
23
24 #include "includes.h"
25 #include "libcli/nbt/libnbt.h"
26 #include "libcli/wrepl/winsrepl.h"
27 #include "lib/events/events.h"
28 #include "lib/socket/socket.h"
29 #include "system/time.h"
30
31 #define CHECK_STATUS(status, correct) do { \
32         if (!NT_STATUS_EQUAL(status, correct)) { \
33                 printf("(%s) Incorrect status %s - should be %s\n", \
34                        __location__, nt_errstr(status), nt_errstr(correct)); \
35                 ret = False; \
36                 goto done; \
37         }} while (0)
38
39 #define CHECK_VALUE(v, correct) do { \
40         if ((v) != (correct)) { \
41                 printf("(%s) Incorrect value %s=%d - should be %d\n", \
42                        __location__, #v, v, correct); \
43                 ret = False; \
44                 goto done; \
45         }} while (0)
46
47 #define CHECK_VALUE_UINT64(v, correct) do { \
48         if ((v) != (correct)) { \
49                 printf("(%s) Incorrect value %s=%llu - should be %llu\n", \
50                        __location__, #v, v, correct); \
51                 ret = False; \
52                 goto done; \
53         }} while (0)
54
55 #define CHECK_VALUE_STRING(v, correct) do { \
56         if ( ((!v) && (correct)) || \
57              ((v) && (!correct)) || \
58              ((v) && (correct) && strcmp(v,correct) != 0)) { \
59                 printf("(%s) Incorrect value %s='%s' - should be '%s'\n", \
60                        __location__, #v, v, correct); \
61                 ret = False; \
62                 goto done; \
63         }} while (0)
64
65 #define _NBT_NAME(n,t,s) {\
66         .name   = n,\
67         .type   = t,\
68         .scope  = s\
69 }
70
71 static const char *wrepl_name_type_string(enum wrepl_name_type type)
72 {
73         switch (type) {
74         case WREPL_TYPE_UNIQUE: return "UNIQUE";
75         case WREPL_TYPE_GROUP: return "GROUP";
76         case WREPL_TYPE_SGROUP: return "SGROUP";
77         case WREPL_TYPE_MHOMED: return "MHOMED";
78         }
79         return "UNKNOWN_TYPE";
80 }
81
82 static const char *wrepl_name_state_string(enum wrepl_name_state state)
83 {
84         switch (state) {
85         case WREPL_STATE_ACTIVE: return "ACTIVE";
86         case WREPL_STATE_RELEASED: return "RELEASED";
87         case WREPL_STATE_TOMBSTONE: return "TOMBSTONE";
88         case WREPL_STATE_RESERVED: return "RESERVED";
89         }
90         return "UNKNOWN_STATE";
91 }
92
93 /*
94   test how assoc_ctx's are only usable on the connection
95   they are created on.
96 */
97 static BOOL test_assoc_ctx1(TALLOC_CTX *mem_ctx, const char *address)
98 {
99         BOOL ret = True;
100         struct wrepl_request *req;
101         struct wrepl_socket *wrepl_socket1;
102         struct wrepl_associate associate1;
103         struct wrepl_socket *wrepl_socket2;
104         struct wrepl_associate associate2;
105         struct wrepl_pull_table pull_table;
106         struct wrepl_packet *rep_packet;
107         struct wrepl_associate_stop assoc_stop;
108         NTSTATUS status;
109
110         if (!lp_parm_bool(-1, "torture", "dangerous", False)) {
111                 printf("winsrepl: cross connection assoc_ctx usage disabled - enable dangerous tests to use\n");
112                 return True;
113         }
114
115         printf("Test if assoc_ctx is only valid on the conection it was created on\n");
116
117         wrepl_socket1 = wrepl_socket_init(mem_ctx, NULL);
118         wrepl_socket2 = wrepl_socket_init(mem_ctx, NULL);
119
120         printf("Setup 2 wrepl connections\n");
121         status = wrepl_connect(wrepl_socket1, NULL, address);
122         CHECK_STATUS(status, NT_STATUS_OK);
123
124         status = wrepl_connect(wrepl_socket2, NULL, address);
125         CHECK_STATUS(status, NT_STATUS_OK);
126
127         printf("Send a start association request (conn1)\n");
128         status = wrepl_associate(wrepl_socket1, &associate1);
129         CHECK_STATUS(status, NT_STATUS_OK);
130
131         printf("association context (conn1): 0x%x\n", associate1.out.assoc_ctx);
132
133         printf("Send a start association request (conn2)\n");
134         status = wrepl_associate(wrepl_socket2, &associate2);
135         CHECK_STATUS(status, NT_STATUS_OK);
136
137         printf("association context (conn2): 0x%x\n", associate2.out.assoc_ctx);
138
139         printf("Send a replication table query, with assoc 1 (conn2), the anwser should be on conn1\n");
140         pull_table.in.assoc_ctx = associate1.out.assoc_ctx;
141         req = wrepl_pull_table_send(wrepl_socket2, &pull_table);
142         req->send_only = True;
143         status = wrepl_request_recv(req, mem_ctx, &rep_packet);
144         CHECK_STATUS(status, NT_STATUS_OK);
145
146         printf("Send a association request (conn2), to make sure the last request was ignored\n");
147         status = wrepl_associate(wrepl_socket2, &associate2);
148         CHECK_STATUS(status, NT_STATUS_OK);
149
150         printf("Send a replication table query, with invalid assoc (conn1), receive answer from conn2\n");
151         pull_table.in.assoc_ctx = 0;
152         req = wrepl_pull_table_send(wrepl_socket1, &pull_table);
153         status = wrepl_request_recv(req, mem_ctx, &rep_packet);
154         CHECK_STATUS(status, NT_STATUS_OK);
155
156         printf("Send a association request (conn1), to make sure the last request was handled correct\n");
157         status = wrepl_associate(wrepl_socket1, &associate2);
158         CHECK_STATUS(status, NT_STATUS_OK);
159
160         assoc_stop.in.assoc_ctx = associate1.out.assoc_ctx;
161         assoc_stop.in.reason    = 4;
162         printf("Send a association stop request (conn1), reson: %u\n", assoc_stop.in.reason);
163         status = wrepl_associate_stop(wrepl_socket1, &assoc_stop);
164         CHECK_STATUS(status, NT_STATUS_END_OF_FILE);
165
166         assoc_stop.in.assoc_ctx = associate2.out.assoc_ctx;
167         assoc_stop.in.reason    = 0;
168         printf("Send a association stop request (conn2), reson: %u\n", assoc_stop.in.reason);
169         status = wrepl_associate_stop(wrepl_socket2, &assoc_stop);
170         CHECK_STATUS(status, NT_STATUS_OK);
171
172 done:
173         printf("Close 2 wrepl connections\n");
174         talloc_free(wrepl_socket1);
175         talloc_free(wrepl_socket2);
176         return ret;
177 }
178
179 /*
180   test if we always get back the same assoc_ctx
181 */
182 static BOOL test_assoc_ctx2(TALLOC_CTX *mem_ctx, const char *address)
183 {
184         BOOL ret = True;
185         struct wrepl_socket *wrepl_socket;
186         struct wrepl_associate associate;
187         uint32_t assoc_ctx1;
188         NTSTATUS status;
189
190         printf("Test if we always get back the same assoc_ctx\n");
191
192         wrepl_socket = wrepl_socket_init(mem_ctx, NULL);
193         
194         printf("Setup wrepl connections\n");
195         status = wrepl_connect(wrepl_socket, NULL, address);
196         CHECK_STATUS(status, NT_STATUS_OK);
197
198
199         printf("Send 1st start association request\n");
200         status = wrepl_associate(wrepl_socket, &associate);
201         CHECK_STATUS(status, NT_STATUS_OK);
202         assoc_ctx1 = associate.out.assoc_ctx;
203         printf("1st association context: 0x%x\n", associate.out.assoc_ctx);
204
205         printf("Send 2nd start association request\n");
206         status = wrepl_associate(wrepl_socket, &associate);
207         CHECK_VALUE(associate.out.assoc_ctx, assoc_ctx1);
208         CHECK_STATUS(status, NT_STATUS_OK);
209         printf("2nd association context: 0x%x\n", associate.out.assoc_ctx);
210
211         printf("Send 3rd start association request\n");
212         status = wrepl_associate(wrepl_socket, &associate);
213         CHECK_VALUE(associate.out.assoc_ctx, assoc_ctx1);
214         CHECK_STATUS(status, NT_STATUS_OK);
215         printf("3rd association context: 0x%x\n", associate.out.assoc_ctx);
216
217 done:
218         printf("Close wrepl connections\n");
219         talloc_free(wrepl_socket);
220         return ret;
221 }
222
223
224 /*
225   display a replication entry
226 */
227 static void display_entry(TALLOC_CTX *mem_ctx, struct wrepl_name *name)
228 {
229         int i;
230
231         printf("%s\n", nbt_name_string(mem_ctx, &name->name));
232         printf("\tTYPE:%u STATE:%u NODE:%u STATIC:%u VERSION_ID: %llu\n",
233                 name->type, name->state, name->node, name->is_static, name->version_id);
234         printf("\tRAW_FLAGS: 0x%08X OWNER: %-15s\n",
235                 name->raw_flags, name->owner);
236         for (i=0;i<name->num_addresses;i++) {
237                 printf("\tADDR: %-15s OWNER: %-15s\n", 
238                         name->addresses[i].address, name->addresses[i].owner);
239         }
240 }
241
242 /*
243   test a full replication dump from a WINS server
244 */
245 static BOOL test_wins_replication(TALLOC_CTX *mem_ctx, const char *address)
246 {
247         BOOL ret = True;
248         struct wrepl_socket *wrepl_socket;
249         NTSTATUS status;
250         int i, j;
251         struct wrepl_associate associate;
252         struct wrepl_pull_table pull_table;
253         struct wrepl_pull_names pull_names;
254
255         printf("Test one pull replication cycle\n");
256
257         wrepl_socket = wrepl_socket_init(mem_ctx, NULL);
258         
259         printf("Setup wrepl connections\n");
260         status = wrepl_connect(wrepl_socket, NULL, address);
261         CHECK_STATUS(status, NT_STATUS_OK);
262
263         printf("Send a start association request\n");
264
265         status = wrepl_associate(wrepl_socket, &associate);
266         CHECK_STATUS(status, NT_STATUS_OK);
267
268         printf("association context: 0x%x\n", associate.out.assoc_ctx);
269
270         printf("Send a replication table query\n");
271         pull_table.in.assoc_ctx = associate.out.assoc_ctx;
272
273         status = wrepl_pull_table(wrepl_socket, mem_ctx, &pull_table);
274         if (NT_STATUS_EQUAL(NT_STATUS_NETWORK_ACCESS_DENIED,status)) {
275                 struct wrepl_packet packet;
276                 struct wrepl_request *req;
277
278                 ZERO_STRUCT(packet);
279                 packet.opcode                      = WREPL_OPCODE_BITS;
280                 packet.assoc_ctx                   = associate.out.assoc_ctx;
281                 packet.mess_type                   = WREPL_STOP_ASSOCIATION;
282                 packet.message.stop.reason         = 0;
283
284                 req = wrepl_request_send(wrepl_socket, &packet);
285                 talloc_free(req);
286
287                 printf("failed - We are not a valid pull partner for the server\n");
288                 ret = False;
289                 goto done;
290         }
291         CHECK_STATUS(status, NT_STATUS_OK);
292
293         printf("Found %d replication partners\n", pull_table.out.num_partners);
294
295         for (i=0;i<pull_table.out.num_partners;i++) {
296                 struct wrepl_wins_owner *partner = &pull_table.out.partners[i];
297                 printf("%s   max_version=%6llu   min_version=%6llu type=%d\n",
298                        partner->address, 
299                        partner->max_version, 
300                        partner->min_version, 
301                        partner->type);
302
303                 pull_names.in.assoc_ctx = associate.out.assoc_ctx;
304                 pull_names.in.partner = *partner;
305                 
306                 status = wrepl_pull_names(wrepl_socket, mem_ctx, &pull_names);
307                 CHECK_STATUS(status, NT_STATUS_OK);
308
309                 printf("Received %d names\n", pull_names.out.num_names);
310
311                 for (j=0;j<pull_names.out.num_names;j++) {
312                         display_entry(mem_ctx, &pull_names.out.names[j]);
313                 }
314         }
315
316 done:
317         printf("Close wrepl connections\n");
318         talloc_free(wrepl_socket);
319         return ret;
320 }
321
322 struct test_wrepl_conflict_conn {
323         const char *address;
324         struct wrepl_socket *pull;
325         uint32_t pull_assoc;
326
327 #define TEST_OWNER_A_ADDRESS "127.65.65.1"
328 #define TEST_ADDRESS_A_PREFIX "127.0.65"
329 #define TEST_OWNER_B_ADDRESS "127.66.66.1"
330 #define TEST_ADDRESS_B_PREFIX "127.0.66"
331 #define TEST_OWNER_X_ADDRESS "127.88.88.1"
332 #define TEST_ADDRESS_X_PREFIX "127.0.88"
333
334         struct wrepl_wins_owner a, b, c, x;
335
336         const char *myaddr;
337         const char *myaddr2;
338         struct nbt_name_socket *nbtsock;
339         struct nbt_name_socket *nbtsock2;
340
341         struct nbt_name_socket *nbtsock_srv;
342         struct nbt_name_socket *nbtsock_srv2;
343
344         uint32_t addresses_best_num;
345         struct wrepl_ip *addresses_best;
346
347         uint32_t addresses_best2_num;
348         struct wrepl_ip *addresses_best2;
349
350         uint32_t addresses_all_num;
351         struct wrepl_ip *addresses_all;
352
353         uint32_t addresses_mhomed_num;
354         struct wrepl_ip *addresses_mhomed;
355 };
356
357 static const struct wrepl_ip addresses_A_1[] = {
358         {
359         .owner  = TEST_OWNER_A_ADDRESS,
360         .ip     = TEST_ADDRESS_A_PREFIX".1"
361         }
362 };
363 static const struct wrepl_ip addresses_A_2[] = {
364         {
365         .owner  = TEST_OWNER_A_ADDRESS,
366         .ip     = TEST_ADDRESS_A_PREFIX".2"
367         }
368 };
369 static const struct wrepl_ip addresses_A_3_4[] = {
370         {
371         .owner  = TEST_OWNER_A_ADDRESS,
372         .ip     = TEST_ADDRESS_A_PREFIX".3"
373         },
374         {
375         .owner  = TEST_OWNER_A_ADDRESS,
376         .ip     = TEST_ADDRESS_A_PREFIX".4"
377         }
378 };
379 static const struct wrepl_ip addresses_A_3_4_X_3_4[] = {
380         {
381         .owner  = TEST_OWNER_A_ADDRESS,
382         .ip     = TEST_ADDRESS_A_PREFIX".3"
383         },
384         {
385         .owner  = TEST_OWNER_A_ADDRESS,
386         .ip     = TEST_ADDRESS_A_PREFIX".4"
387         },
388         {
389         .owner  = TEST_OWNER_X_ADDRESS,
390         .ip     = TEST_ADDRESS_X_PREFIX".3"
391         },
392         {
393         .owner  = TEST_OWNER_X_ADDRESS,
394         .ip     = TEST_ADDRESS_X_PREFIX".4"
395         }
396 };
397 static const struct wrepl_ip addresses_A_3_4_OWNER_B[] = {
398         {
399         .owner  = TEST_OWNER_B_ADDRESS,
400         .ip     = TEST_ADDRESS_A_PREFIX".3"
401         },
402         {
403         .owner  = TEST_OWNER_B_ADDRESS,
404         .ip     = TEST_ADDRESS_A_PREFIX".4"
405         }
406 };
407 static const struct wrepl_ip addresses_A_3_4_X_3_4_OWNER_B[] = {
408         {
409         .owner  = TEST_OWNER_B_ADDRESS,
410         .ip     = TEST_ADDRESS_A_PREFIX".3"
411         },
412         {
413         .owner  = TEST_OWNER_B_ADDRESS,
414         .ip     = TEST_ADDRESS_A_PREFIX".4"
415         },
416         {
417         .owner  = TEST_OWNER_B_ADDRESS,
418         .ip     = TEST_ADDRESS_X_PREFIX".3"
419         },
420         {
421         .owner  = TEST_OWNER_B_ADDRESS,
422         .ip     = TEST_ADDRESS_X_PREFIX".4"
423         }
424 };
425
426 static const struct wrepl_ip addresses_A_3_4_X_1_2[] = {
427         {
428         .owner  = TEST_OWNER_A_ADDRESS,
429         .ip     = TEST_ADDRESS_A_PREFIX".3"
430         },
431         {
432         .owner  = TEST_OWNER_A_ADDRESS,
433         .ip     = TEST_ADDRESS_A_PREFIX".4"
434         },
435         {
436         .owner  = TEST_OWNER_X_ADDRESS,
437         .ip     = TEST_ADDRESS_X_PREFIX".1"
438         },
439         {
440         .owner  = TEST_OWNER_X_ADDRESS,
441         .ip     = TEST_ADDRESS_X_PREFIX".2"
442         }
443 };
444
445 static const struct wrepl_ip addresses_B_1[] = {
446         {
447         .owner  = TEST_OWNER_B_ADDRESS,
448         .ip     = TEST_ADDRESS_B_PREFIX".1"
449         }
450 };
451 static const struct wrepl_ip addresses_B_2[] = {
452         {
453         .owner  = TEST_OWNER_B_ADDRESS,
454         .ip     = TEST_ADDRESS_B_PREFIX".2"
455         }
456 };
457 static const struct wrepl_ip addresses_B_3_4[] = {
458         {
459         .owner  = TEST_OWNER_B_ADDRESS,
460         .ip     = TEST_ADDRESS_B_PREFIX".3"
461         },
462         {
463         .owner  = TEST_OWNER_B_ADDRESS,
464         .ip     = TEST_ADDRESS_B_PREFIX".4"
465         }
466 };
467 static const struct wrepl_ip addresses_B_3_4_X_3_4[] = {
468         {
469         .owner  = TEST_OWNER_B_ADDRESS,
470         .ip     = TEST_ADDRESS_B_PREFIX".3"
471         },
472         {
473         .owner  = TEST_OWNER_B_ADDRESS,
474         .ip     = TEST_ADDRESS_B_PREFIX".4"
475         },
476         {
477         .owner  = TEST_OWNER_X_ADDRESS,
478         .ip     = TEST_ADDRESS_X_PREFIX".3"
479         },
480         {
481         .owner  = TEST_OWNER_X_ADDRESS,
482         .ip     = TEST_ADDRESS_X_PREFIX".4"
483         }
484 };
485 static const struct wrepl_ip addresses_B_3_4_X_1_2[] = {
486         {
487         .owner  = TEST_OWNER_B_ADDRESS,
488         .ip     = TEST_ADDRESS_B_PREFIX".3"
489         },
490         {
491         .owner  = TEST_OWNER_B_ADDRESS,
492         .ip     = TEST_ADDRESS_B_PREFIX".4"
493         },
494         {
495         .owner  = TEST_OWNER_X_ADDRESS,
496         .ip     = TEST_ADDRESS_X_PREFIX".1"
497         },
498         {
499         .owner  = TEST_OWNER_X_ADDRESS,
500         .ip     = TEST_ADDRESS_X_PREFIX".2"
501         }
502 };
503
504 static struct test_wrepl_conflict_conn *test_create_conflict_ctx(TALLOC_CTX *mem_ctx,
505                                                                  const char *address)
506 {
507         struct test_wrepl_conflict_conn *ctx;
508         struct wrepl_associate associate;
509         struct wrepl_pull_table pull_table;
510         NTSTATUS status;
511         uint32_t i;
512
513         ctx = talloc_zero(mem_ctx, struct test_wrepl_conflict_conn);
514         if (!ctx) return NULL;
515
516         ctx->address    = address;
517         ctx->pull       = wrepl_socket_init(ctx, NULL);
518         if (!ctx->pull) return NULL;
519
520         printf("Setup wrepl conflict pull connection\n");
521         status = wrepl_connect(ctx->pull, NULL, ctx->address);
522         if (!NT_STATUS_IS_OK(status)) return NULL;
523
524         status = wrepl_associate(ctx->pull, &associate);
525         if (!NT_STATUS_IS_OK(status)) return NULL;
526
527         ctx->pull_assoc = associate.out.assoc_ctx;
528
529         ctx->a.address          = TEST_OWNER_A_ADDRESS;
530         ctx->a.max_version      = 0;
531         ctx->a.min_version      = 0;
532         ctx->a.type             = 1;
533
534         ctx->b.address          = TEST_OWNER_B_ADDRESS;
535         ctx->b.max_version      = 0;
536         ctx->b.min_version      = 0;
537         ctx->b.type             = 1;
538
539         ctx->x.address          = TEST_OWNER_X_ADDRESS;
540         ctx->x.max_version      = 0;
541         ctx->x.min_version      = 0;
542         ctx->x.type             = 1;
543
544         ctx->c.address          = address;
545         ctx->c.max_version      = 0;
546         ctx->c.min_version      = 0;
547         ctx->c.type             = 1;
548
549         pull_table.in.assoc_ctx = ctx->pull_assoc;
550         status = wrepl_pull_table(ctx->pull, ctx->pull, &pull_table);
551         if (!NT_STATUS_IS_OK(status)) return NULL;
552
553         for (i=0; i < pull_table.out.num_partners; i++) {
554                 if (strcmp(TEST_OWNER_A_ADDRESS,pull_table.out.partners[i].address)==0) {
555                         ctx->a.max_version      = pull_table.out.partners[i].max_version;
556                         ctx->a.min_version      = pull_table.out.partners[i].min_version;
557                 }
558                 if (strcmp(TEST_OWNER_B_ADDRESS,pull_table.out.partners[i].address)==0) {
559                         ctx->b.max_version      = pull_table.out.partners[i].max_version;
560                         ctx->b.min_version      = pull_table.out.partners[i].min_version;
561                 }
562                 if (strcmp(TEST_OWNER_X_ADDRESS,pull_table.out.partners[i].address)==0) {
563                         ctx->x.max_version      = pull_table.out.partners[i].max_version;
564                         ctx->x.min_version      = pull_table.out.partners[i].min_version;
565                 }
566                 if (strcmp(address,pull_table.out.partners[i].address)==0) {
567                         ctx->c.max_version      = pull_table.out.partners[i].max_version;
568                         ctx->c.min_version      = pull_table.out.partners[i].min_version;
569                 }
570         }
571
572         talloc_free(pull_table.out.partners);
573
574         ctx->myaddr = talloc_strdup(mem_ctx, iface_best_ip(address));
575         if (!ctx->myaddr) return NULL;
576
577         for (i = 0; i < iface_count(); i++) {
578                 if (strcmp(ctx->myaddr, iface_n_ip(i)) == 0) continue;
579                 ctx->myaddr2 = talloc_strdup(mem_ctx, iface_n_ip(i));
580                 if (!ctx->myaddr2) return NULL;
581                 break;
582         }
583
584         ctx->nbtsock = nbt_name_socket_init(ctx, NULL);
585         if (!ctx->nbtsock) return NULL;
586
587         status = socket_listen(ctx->nbtsock->sock, ctx->myaddr, 0, 0, 0);
588         if (!NT_STATUS_IS_OK(status)) return NULL;
589
590         ctx->nbtsock_srv = nbt_name_socket_init(ctx, NULL);
591         if (!ctx->nbtsock_srv) return NULL;
592
593         status = socket_listen(ctx->nbtsock_srv->sock, ctx->myaddr, lp_nbt_port(), 0, 0);
594         if (!NT_STATUS_IS_OK(status)) {
595                 talloc_free(ctx->nbtsock_srv);
596                 ctx->nbtsock_srv = NULL;
597         }
598
599         if (ctx->myaddr2 && ctx->nbtsock_srv) {
600                 ctx->nbtsock2 = nbt_name_socket_init(ctx, NULL);
601                 if (!ctx->nbtsock2) return NULL;
602
603                 status = socket_listen(ctx->nbtsock2->sock, ctx->myaddr2, 0, 0, 0);
604                 if (!NT_STATUS_IS_OK(status)) return NULL;
605
606                 ctx->nbtsock_srv2 = nbt_name_socket_init(ctx, ctx->nbtsock_srv->event_ctx);
607                 if (!ctx->nbtsock_srv2) return NULL;
608
609                 status = socket_listen(ctx->nbtsock_srv2->sock, ctx->myaddr2, lp_nbt_port(), 0, 0);
610                 if (!NT_STATUS_IS_OK(status)) {
611                         talloc_free(ctx->nbtsock_srv2);
612                         ctx->nbtsock_srv2 = NULL;
613                 }
614         }
615
616         ctx->addresses_best_num = 1;
617         ctx->addresses_best = talloc_array(ctx, struct wrepl_ip, ctx->addresses_best_num);
618         if (!ctx->addresses_best) return NULL;
619         ctx->addresses_best[0].owner    = ctx->b.address;
620         ctx->addresses_best[0].ip       = ctx->myaddr;
621
622         ctx->addresses_all_num = iface_count();
623         ctx->addresses_all = talloc_array(ctx, struct wrepl_ip, ctx->addresses_all_num);
624         if (!ctx->addresses_all) return NULL;
625         for (i=0; i < ctx->addresses_all_num; i++) {
626                 ctx->addresses_all[i].owner     = ctx->b.address;
627                 ctx->addresses_all[i].ip        = talloc_strdup(ctx->addresses_all, iface_n_ip(i));
628                 if (!ctx->addresses_all[i].ip) return NULL;
629         }
630
631         if (ctx->nbtsock_srv2) {
632                 ctx->addresses_best2_num = 1;
633                 ctx->addresses_best2 = talloc_array(ctx, struct wrepl_ip, ctx->addresses_best2_num);
634                 if (!ctx->addresses_best2) return NULL;
635                 ctx->addresses_best2[0].owner   = ctx->b.address;
636                 ctx->addresses_best2[0].ip      = ctx->myaddr2;
637
638                 ctx->addresses_mhomed_num = 2;
639                 ctx->addresses_mhomed = talloc_array(ctx, struct wrepl_ip, ctx->addresses_mhomed_num);
640                 if (!ctx->addresses_mhomed) return NULL;
641                 ctx->addresses_mhomed[0].owner  = ctx->b.address;
642                 ctx->addresses_mhomed[0].ip     = ctx->myaddr;
643                 ctx->addresses_mhomed[1].owner  = ctx->b.address;
644                 ctx->addresses_mhomed[1].ip     = ctx->myaddr2;
645         }
646
647         return ctx;
648 }
649
650 static BOOL test_wrepl_update_one(struct test_wrepl_conflict_conn *ctx,
651                                   const struct wrepl_wins_owner *owner,
652                                   const struct wrepl_wins_name *name)
653 {
654         BOOL ret = True;
655         struct wrepl_socket *wrepl_socket;
656         struct wrepl_associate associate;
657         struct wrepl_packet update_packet, repl_send;
658         struct wrepl_table *update;
659         struct wrepl_wins_owner wrepl_wins_owners[1];
660         struct wrepl_packet *repl_recv;
661         struct wrepl_wins_owner *send_request;
662         struct wrepl_send_reply *send_reply;
663         struct wrepl_wins_name wrepl_wins_names[1];
664         uint32_t assoc_ctx;
665         NTSTATUS status;
666
667         wrepl_socket = wrepl_socket_init(ctx, NULL);
668
669         status = wrepl_connect(wrepl_socket, NULL, ctx->address);
670         CHECK_STATUS(status, NT_STATUS_OK);
671
672         status = wrepl_associate(wrepl_socket, &associate);
673         CHECK_STATUS(status, NT_STATUS_OK);
674         assoc_ctx = associate.out.assoc_ctx;
675
676         /* now send a WREPL_REPL_UPDATE message */
677         ZERO_STRUCT(update_packet);
678         update_packet.opcode                    = WREPL_OPCODE_BITS;
679         update_packet.assoc_ctx                 = assoc_ctx;
680         update_packet.mess_type                 = WREPL_REPLICATION;
681         update_packet.message.replication.command       = WREPL_REPL_UPDATE;
682         update  = &update_packet.message.replication.info.table;
683
684         update->partner_count   = ARRAY_SIZE(wrepl_wins_owners);
685         update->partners        = wrepl_wins_owners;
686         update->initiator       = "0.0.0.0";
687
688         wrepl_wins_owners[0]    = *owner;
689
690         status = wrepl_request(wrepl_socket, wrepl_socket,
691                                &update_packet, &repl_recv);
692         CHECK_STATUS(status, NT_STATUS_OK);
693         CHECK_VALUE(repl_recv->mess_type, WREPL_REPLICATION);
694         CHECK_VALUE(repl_recv->message.replication.command, WREPL_REPL_SEND_REQUEST);
695         send_request = &repl_recv->message.replication.info.owner;
696
697         ZERO_STRUCT(repl_send);
698         repl_send.opcode                        = WREPL_OPCODE_BITS;
699         repl_send.assoc_ctx                     = assoc_ctx;
700         repl_send.mess_type                     = WREPL_REPLICATION;
701         repl_send.message.replication.command   = WREPL_REPL_SEND_REPLY;
702         send_reply = &repl_send.message.replication.info.reply;
703
704         send_reply->num_names   = ARRAY_SIZE(wrepl_wins_names);
705         send_reply->names       = wrepl_wins_names;
706
707         wrepl_wins_names[0]     = *name;
708
709         status = wrepl_request(wrepl_socket, wrepl_socket,
710                                &repl_send, &repl_recv);
711         CHECK_STATUS(status, NT_STATUS_OK);
712         CHECK_VALUE(repl_recv->mess_type, WREPL_STOP_ASSOCIATION);
713         CHECK_VALUE(repl_recv->message.stop.reason, 0);
714
715 done:
716         talloc_free(wrepl_socket);
717         return ret;
718 }
719
720 static BOOL test_wrepl_is_applied(struct test_wrepl_conflict_conn *ctx,
721                                   const struct wrepl_wins_owner *owner,
722                                   const struct wrepl_wins_name *name,
723                                   BOOL expected)
724 {
725         BOOL ret = True;
726         NTSTATUS status;
727         struct wrepl_pull_names pull_names;
728         struct wrepl_name *names;
729
730         pull_names.in.assoc_ctx = ctx->pull_assoc;
731         pull_names.in.partner   = *owner;
732         pull_names.in.partner.min_version = pull_names.in.partner.max_version;
733                 
734         status = wrepl_pull_names(ctx->pull, ctx->pull, &pull_names);
735         CHECK_STATUS(status, NT_STATUS_OK);
736         CHECK_VALUE(pull_names.out.num_names, (expected?1:0));
737
738         names = pull_names.out.names;
739
740         if (expected) {
741                 uint32_t flags = WREPL_NAME_FLAGS(names[0].type,
742                                                   names[0].state,
743                                                   names[0].node,
744                                                   names[0].is_static);
745                 CHECK_VALUE(names[0].name.type, name->name->type);
746                 CHECK_VALUE_STRING(names[0].name.name, name->name->name);
747                 CHECK_VALUE_STRING(names[0].name.scope, name->name->scope);
748                 CHECK_VALUE(flags, name->flags);
749                 CHECK_VALUE_UINT64(names[0].version_id, name->id);
750
751                 if (flags & 2) {
752                         CHECK_VALUE(names[0].num_addresses,
753                                     name->addresses.addresses.num_ips);
754                 } else {
755                         CHECK_VALUE(names[0].num_addresses, 1);
756                         CHECK_VALUE_STRING(names[0].addresses[0].address,
757                                            name->addresses.ip);
758                 }
759         }
760 done:
761         talloc_free(pull_names.out.names);
762         return ret;
763 }
764
765 static BOOL test_wrepl_mhomed_merged(struct test_wrepl_conflict_conn *ctx,
766                                      const struct wrepl_wins_owner *owner1,
767                                      uint32_t num_ips1, const struct wrepl_ip *ips1,
768                                      const struct wrepl_wins_owner *owner2,
769                                      uint32_t num_ips2, const struct wrepl_ip *ips2,
770                                      const struct wrepl_wins_name *name2)
771 {
772         BOOL ret = True;
773         NTSTATUS status;
774         struct wrepl_pull_names pull_names;
775         struct wrepl_name *names;
776         uint32_t flags;
777         uint32_t i, j;
778         uint32_t num_ips = num_ips1 + num_ips2;
779
780         for (i = 0; i < num_ips2; i++) {
781                 for (j = 0; j < num_ips1; j++) {
782                         if (strcmp(ips2[i].ip,ips1[j].ip) == 0) {
783                                 num_ips--;
784                                 break;
785                         }
786                 } 
787         }
788
789         pull_names.in.assoc_ctx = ctx->pull_assoc;
790         pull_names.in.partner   = *owner2;
791         pull_names.in.partner.min_version = pull_names.in.partner.max_version;
792
793         status = wrepl_pull_names(ctx->pull, ctx->pull, &pull_names);
794         CHECK_STATUS(status, NT_STATUS_OK);
795         CHECK_VALUE(pull_names.out.num_names, 1);
796
797         names = pull_names.out.names;
798
799         flags = WREPL_NAME_FLAGS(names[0].type,
800                                  names[0].state,
801                                  names[0].node,
802                                  names[0].is_static);
803         CHECK_VALUE(names[0].name.type, name2->name->type);
804         CHECK_VALUE_STRING(names[0].name.name, name2->name->name);
805         CHECK_VALUE_STRING(names[0].name.scope, name2->name->scope);
806         CHECK_VALUE(flags, name2->flags | WREPL_TYPE_MHOMED);
807         CHECK_VALUE_UINT64(names[0].version_id, name2->id);
808
809         CHECK_VALUE(names[0].num_addresses, num_ips);
810
811         for (i = 0; i < names[0].num_addresses; i++) {
812                 const char *addr = names[0].addresses[i].address; 
813                 const char *owner = names[0].addresses[i].owner;
814                 BOOL found = False;
815
816                 for (j = 0; j < num_ips2; j++) {
817                         if (strcmp(addr, ips2[j].ip) == 0) {
818                                 found = True;
819                                 CHECK_VALUE_STRING(owner, owner2->address);
820                                 break;
821                         }
822                 }
823
824                 if (found) continue;
825
826                 for (j = 0; j < num_ips1; j++) {
827                         if (strcmp(addr, ips1[j].ip) == 0) {
828                                 found = True;
829                                 CHECK_VALUE_STRING(owner, owner1->address);
830                                 break;
831                         }
832                 }
833
834                 if (found) continue;
835
836                 CHECK_VALUE_STRING(addr, "not found in address list");
837         }
838 done:
839         talloc_free(pull_names.out.names);
840         return ret;
841 }
842
843 static BOOL test_wrepl_sgroup_merged(struct test_wrepl_conflict_conn *ctx,
844                                      struct wrepl_wins_owner *merge_owner,
845                                      struct wrepl_wins_owner *owner1,
846                                      uint32_t num_ips1, const struct wrepl_ip *ips1,
847                                      struct wrepl_wins_owner *owner2,
848                                      uint32_t num_ips2, const struct wrepl_ip *ips2,
849                                      const struct wrepl_wins_name *name2)
850 {
851         BOOL ret = True;
852         NTSTATUS status;
853         struct wrepl_pull_names pull_names;
854         struct wrepl_name *names;
855         struct wrepl_name *name = NULL;
856         uint32_t flags;
857         uint32_t i, j;
858         uint32_t num_ips = num_ips1 + num_ips2;
859
860         if (!merge_owner) {
861                 merge_owner = &ctx->c;
862         }
863
864         for (i = 0; i < num_ips1; i++) {
865                 if (owner1 != &ctx->c && strcmp(ips1[i].owner,owner2->address) == 0) {
866                         num_ips--;
867                         continue;
868                 }
869                 for (j = 0; j < num_ips2; j++) {
870                         if (strcmp(ips1[i].ip,ips2[j].ip) == 0) {
871                                 num_ips--;
872                                 break;
873                         }
874                 }
875         }
876
877
878         pull_names.in.assoc_ctx = ctx->pull_assoc;
879         pull_names.in.partner   = *merge_owner;
880         pull_names.in.partner.min_version = pull_names.in.partner.max_version;
881         pull_names.in.partner.max_version = 0;
882
883         status = wrepl_pull_names(ctx->pull, ctx->pull, &pull_names);
884         CHECK_STATUS(status, NT_STATUS_OK);
885
886         names = pull_names.out.names;
887         
888         for (i = 0; i < pull_names.out.num_names; i++) {
889                 if (names[i].name.type != name2->name->type)    continue;
890                 if (!names[i].name.name) continue;
891                 if (strcmp(names[i].name.name, name2->name->name) != 0) continue;
892                 if (names[i].name.scope) continue;
893
894                 name = &names[i];
895         }
896
897         if (pull_names.out.num_names > 0) {
898                 merge_owner->max_version        = names[pull_names.out.num_names-1].version_id;
899         }
900
901         if (!name) {
902                 printf("%s: Name '%s' not found\n", __location__, nbt_name_string(ctx, name2->name));
903                 return False;
904         }
905
906         flags = WREPL_NAME_FLAGS(name->type,
907                                  name->state,
908                                  name->node,
909                                  name->is_static);
910         CHECK_VALUE(name->name.type, name2->name->type);
911         CHECK_VALUE_STRING(name->name.name, name2->name->name);
912         CHECK_VALUE_STRING(name->name.scope, name2->name->scope);
913         CHECK_VALUE(flags, name2->flags);
914
915         CHECK_VALUE(name->num_addresses, num_ips);
916
917         for (i = 0; i < name->num_addresses; i++) {
918                 const char *addr = name->addresses[i].address; 
919                 const char *owner = name->addresses[i].owner;
920                 BOOL found = False;
921
922                 for (j = 0; j < num_ips2; j++) {
923                         if (strcmp(addr, ips2[j].ip) == 0) {
924                                 found = True;
925                                 CHECK_VALUE_STRING(owner, ips2[j].owner);
926                                 break;
927                         }
928                 }
929
930                 if (found) continue;
931
932                 for (j = 0; j < num_ips1; j++) {
933                         if (strcmp(addr, ips1[j].ip) == 0) {
934                                 found = True;
935                                 if (owner1 == &ctx->c) {
936                                         CHECK_VALUE_STRING(owner, owner1->address);
937                                 } else {
938                                         CHECK_VALUE_STRING(owner, ips1[j].owner);
939                                 }
940                                 break;
941                         }
942                 }
943
944                 if (found) continue;
945
946                 CHECK_VALUE_STRING(addr, "not found in address list");
947         }
948 done:
949         talloc_free(pull_names.out.names);
950         return ret;
951 }
952
953 static BOOL test_conflict_same_owner(struct test_wrepl_conflict_conn *ctx)
954 {
955         BOOL ret = True;
956         struct nbt_name name;
957         struct wrepl_wins_name wins_name1;
958         struct wrepl_wins_name wins_name2;
959         struct wrepl_wins_name *wins_name_tmp;
960         struct wrepl_wins_name *wins_name_last;
961         struct wrepl_wins_name *wins_name_cur;
962         uint32_t i,j;
963         uint8_t types[] = { 0x00, 0x1C };
964         struct {
965                 enum wrepl_name_type type;
966                 enum wrepl_name_state state;
967                 enum wrepl_name_node node;
968                 BOOL is_static;
969                 uint32_t num_ips;
970                 const struct wrepl_ip *ips;
971         } records[] = {
972                 {
973                 .type           = WREPL_TYPE_GROUP,
974                 .state          = WREPL_STATE_ACTIVE,
975                 .node           = WREPL_NODE_B,
976                 .is_static      = False,
977                 .num_ips        = ARRAY_SIZE(addresses_A_1),
978                 .ips            = addresses_A_1,
979                 },{
980                 .type           = WREPL_TYPE_UNIQUE,
981                 .state          = WREPL_STATE_ACTIVE,
982                 .node           = WREPL_NODE_B,
983                 .is_static      = False,
984                 .num_ips        = ARRAY_SIZE(addresses_A_1),
985                 .ips            = addresses_A_1,
986                 },{
987                 .type           = WREPL_TYPE_UNIQUE,
988                 .state          = WREPL_STATE_ACTIVE,
989                 .node           = WREPL_NODE_B,
990                 .is_static      = False,
991                 .num_ips        = ARRAY_SIZE(addresses_A_2),
992                 .ips            = addresses_A_2,
993                 },{
994                 .type           = WREPL_TYPE_UNIQUE,
995                 .state          = WREPL_STATE_ACTIVE,
996                 .node           = WREPL_NODE_B,
997                 .is_static      = True,
998                 .num_ips        = ARRAY_SIZE(addresses_A_1),
999                 .ips            = addresses_A_1,
1000                 },{
1001                 .type           = WREPL_TYPE_UNIQUE,
1002                 .state          = WREPL_STATE_ACTIVE,
1003                 .node           = WREPL_NODE_B,
1004                 .is_static      = False,
1005                 .num_ips        = ARRAY_SIZE(addresses_A_2),
1006                 .ips            = addresses_A_2,
1007                 },{
1008                 .type           = WREPL_TYPE_SGROUP,
1009                 .state          = WREPL_STATE_TOMBSTONE,
1010                 .node           = WREPL_NODE_B,
1011                 .is_static      = False,
1012                 .num_ips        = ARRAY_SIZE(addresses_A_2),
1013                 .ips            = addresses_A_2,
1014                 },{
1015                 .type           = WREPL_TYPE_MHOMED,
1016                 .state          = WREPL_STATE_TOMBSTONE,
1017                 .node           = WREPL_NODE_B,
1018                 .is_static      = False,
1019                 .num_ips        = ARRAY_SIZE(addresses_A_1),
1020                 .ips            = addresses_A_1,
1021                 },{
1022                 .type           = WREPL_TYPE_MHOMED,
1023                 .state          = WREPL_STATE_RELEASED,
1024                 .node           = WREPL_NODE_B,
1025                 .is_static      = False,
1026                 .num_ips        = ARRAY_SIZE(addresses_A_2),
1027                 .ips            = addresses_A_2,
1028                 },{
1029                 .type           = WREPL_TYPE_SGROUP,
1030                 .state          = WREPL_STATE_ACTIVE,
1031                 .node           = WREPL_NODE_B,
1032                 .is_static      = False,
1033                 .num_ips        = ARRAY_SIZE(addresses_A_1),
1034                 .ips            = addresses_A_1,
1035                 },{
1036                 .type           = WREPL_TYPE_SGROUP,
1037                 .state          = WREPL_STATE_ACTIVE,
1038                 .node           = WREPL_NODE_B,
1039                 .is_static      = False,
1040                 .num_ips        = ARRAY_SIZE(addresses_A_3_4),
1041                 .ips            = addresses_A_3_4,
1042                 },{
1043                 .type           = WREPL_TYPE_SGROUP,
1044                 .state          = WREPL_STATE_TOMBSTONE,
1045                 .node           = WREPL_NODE_B,
1046                 .is_static      = False,
1047                 .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1048                 .ips            = addresses_B_3_4,
1049                 },{
1050                 /* the last one should always be a unique,tomstone record! */
1051                 .type           = WREPL_TYPE_UNIQUE,
1052                 .state          = WREPL_STATE_TOMBSTONE,
1053                 .node           = WREPL_NODE_B,
1054                 .is_static      = False,
1055                 .num_ips        = ARRAY_SIZE(addresses_A_1),
1056                 .ips            = addresses_A_1,
1057                 }
1058         };
1059
1060         if (!ctx) return False;
1061
1062         name.name       = "_SAME_OWNER_A";
1063         name.type       = 0;
1064         name.scope      = NULL;
1065
1066         wins_name_tmp   = NULL;
1067         wins_name_last  = &wins_name2;
1068         wins_name_cur   = &wins_name1;
1069
1070         for (j=0; ret && j < ARRAY_SIZE(types); j++) {
1071                 name.type = types[j];
1072                 printf("Test Replica Conflicts with same owner[%s] for %s\n",
1073                         nbt_name_string(ctx, &name), ctx->a.address);
1074
1075                 for(i=0; ret && i < ARRAY_SIZE(records); i++) {
1076                         wins_name_tmp   = wins_name_last;
1077                         wins_name_last  = wins_name_cur;
1078                         wins_name_cur   = wins_name_tmp;
1079
1080                         if (i > 0) {
1081                                 printf("%s,%s%s vs. %s,%s%s with %s ip(s) => %s\n",
1082                                         wrepl_name_type_string(records[i-1].type),
1083                                         wrepl_name_state_string(records[i-1].state),
1084                                         (records[i-1].is_static?",static":""),
1085                                         wrepl_name_type_string(records[i].type),
1086                                         wrepl_name_state_string(records[i].state),
1087                                         (records[i].is_static?",static":""),
1088                                         (records[i-1].ips==records[i].ips?"same":"different"),
1089                                         "REPLACE");
1090                         }
1091
1092                         wins_name_cur->name     = &name;
1093                         wins_name_cur->flags    = WREPL_NAME_FLAGS(records[i].type,
1094                                                                    records[i].state,
1095                                                                    records[i].node,
1096                                                                    records[i].is_static);
1097                         wins_name_cur->id       = ++ctx->a.max_version;
1098                         if (wins_name_cur->flags & 2) {
1099                                 wins_name_cur->addresses.addresses.num_ips = records[i].num_ips;
1100                                 wins_name_cur->addresses.addresses.ips     = discard_const(records[i].ips);
1101                         } else {
1102                                 wins_name_cur->addresses.ip = records[i].ips[0].ip;
1103                         }
1104                         wins_name_cur->unknown  = "255.255.255.255";
1105
1106                         ret &= test_wrepl_update_one(ctx, &ctx->a,wins_name_cur);
1107                         if (records[i].state == WREPL_STATE_RELEASED) {
1108                                 ret &= test_wrepl_is_applied(ctx, &ctx->a, wins_name_last, False);
1109                                 ret &= test_wrepl_is_applied(ctx, &ctx->a, wins_name_cur, False);
1110                         } else {
1111                                 ret &= test_wrepl_is_applied(ctx, &ctx->a, wins_name_cur, True);
1112                         }
1113
1114                         /* the first one is a cleanup run */
1115                         if (!ret && i == 0) ret = True;
1116
1117                         if (!ret) {
1118                                 printf("conflict handled wrong or record[%u]: %s\n", i, __location__);
1119                                 return ret;
1120                         }
1121                 }
1122         }
1123         return ret;
1124 }
1125
1126 static BOOL test_conflict_different_owner(struct test_wrepl_conflict_conn *ctx)
1127 {
1128         BOOL ret = True;
1129         struct wrepl_wins_name wins_name1;
1130         struct wrepl_wins_name wins_name2;
1131         struct wrepl_wins_name *wins_name_r1;
1132         struct wrepl_wins_name *wins_name_r2;
1133         uint32_t i;
1134         struct {
1135                 const char *line; /* just better debugging */
1136                 struct nbt_name name;
1137                 const char *comment;
1138                 BOOL extra; /* not the worst case, this is an extra test */
1139                 BOOL cleanup;
1140                 struct {
1141                         struct wrepl_wins_owner *owner;
1142                         enum wrepl_name_type type;
1143                         enum wrepl_name_state state;
1144                         enum wrepl_name_node node;
1145                         BOOL is_static;
1146                         uint32_t num_ips;
1147                         const struct wrepl_ip *ips;
1148                         BOOL apply_expected;
1149                         BOOL sgroup_merge;
1150                         struct wrepl_wins_owner *merge_owner;
1151                         BOOL sgroup_cleanup;
1152                 } r1, r2, result;
1153         } records[] = {
1154         /* 
1155          * NOTE: the first record and the last applied one
1156          *       needs to be from the same owner,
1157          *       to not conflict in the next smbtorture run!!!
1158          */
1159         {
1160                 .line   = __location__,
1161                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1162                 .cleanup= True,
1163                 .r1     = {
1164                         .owner          = &ctx->b,
1165                         .type           = WREPL_TYPE_UNIQUE,
1166                         .state          = WREPL_STATE_TOMBSTONE,
1167                         .node           = WREPL_NODE_B,
1168                         .is_static      = False,
1169                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1170                         .ips            = addresses_B_1,
1171                         .apply_expected = True /* ignored */
1172                 },
1173                 .r2     = {
1174                         .owner          = &ctx->a,
1175                         .type           = WREPL_TYPE_UNIQUE,
1176                         .state          = WREPL_STATE_TOMBSTONE,
1177                         .node           = WREPL_NODE_B,
1178                         .is_static      = False,
1179                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1180                         .ips            = addresses_A_1,
1181                         .apply_expected = True /* ignored */
1182                 }
1183         },
1184
1185 /*
1186  * unique vs unique section
1187  */
1188         /* 
1189          * unique,active vs. unique,active
1190          * => should be replaced
1191          */
1192         {
1193                 .line   = __location__,
1194                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1195                 .r1     = {
1196                         .owner          = &ctx->a,
1197                         .type           = WREPL_TYPE_UNIQUE,
1198                         .state          = WREPL_STATE_ACTIVE,
1199                         .node           = WREPL_NODE_B,
1200                         .is_static      = False,
1201                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1202                         .ips            = addresses_A_1,
1203                         .apply_expected = True
1204                 },
1205                 .r2     = {
1206                         .owner          = &ctx->b,
1207                         .type           = WREPL_TYPE_UNIQUE,
1208                         .state          = WREPL_STATE_ACTIVE,
1209                         .node           = WREPL_NODE_B,
1210                         .is_static      = False,
1211                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1212                         .ips            = addresses_B_1,
1213                         .apply_expected = True
1214                 }
1215         },
1216
1217         /* 
1218          * unique,active vs. unique,tombstone
1219          * => should NOT be replaced
1220          */
1221         {
1222                 .line   = __location__,
1223                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1224                 .r1     = {
1225                         .owner          = &ctx->b,
1226                         .type           = WREPL_TYPE_UNIQUE,
1227                         .state          = WREPL_STATE_ACTIVE,
1228                         .node           = WREPL_NODE_B,
1229                         .is_static      = False,
1230                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1231                         .ips            = addresses_B_1,
1232                         .apply_expected = True
1233                 },
1234                 .r2     = {
1235                         .owner          = &ctx->a,
1236                         .type           = WREPL_TYPE_UNIQUE,
1237                         .state          = WREPL_STATE_TOMBSTONE,
1238                         .node           = WREPL_NODE_B,
1239                         .is_static      = False,
1240                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1241                         .ips            = addresses_B_1,
1242                         .apply_expected = False
1243                 }
1244         },
1245
1246         /* 
1247          * unique,released vs. unique,active
1248          * => should be replaced
1249          */
1250         {
1251                 .line   = __location__,
1252                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1253                 .r1     = {
1254                         .owner          = &ctx->b,
1255                         .type           = WREPL_TYPE_UNIQUE,
1256                         .state          = WREPL_STATE_RELEASED,
1257                         .node           = WREPL_NODE_B,
1258                         .is_static      = False,
1259                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1260                         .ips            = addresses_B_1,
1261                         .apply_expected = False
1262                 },
1263                 .r2     = {
1264                         .owner          = &ctx->a,
1265                         .type           = WREPL_TYPE_UNIQUE,
1266                         .state          = WREPL_STATE_ACTIVE,
1267                         .node           = WREPL_NODE_B,
1268                         .is_static      = False,
1269                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1270                         .ips            = addresses_A_1,
1271                         .apply_expected = True
1272                 }
1273         },
1274
1275         /* 
1276          * unique,released vs. unique,tombstone
1277          * => should be replaced
1278          */
1279         {
1280                 .line   = __location__,
1281                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1282                 .r1     = {
1283                         .owner          = &ctx->a,
1284                         .type           = WREPL_TYPE_UNIQUE,
1285                         .state          = WREPL_STATE_RELEASED,
1286                         .node           = WREPL_NODE_B,
1287                         .is_static      = False,
1288                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1289                         .ips            = addresses_A_1,
1290                         .apply_expected = False
1291                 },
1292                 .r2     = {
1293                         .owner          = &ctx->b,
1294                         .type           = WREPL_TYPE_UNIQUE,
1295                         .state          = WREPL_STATE_TOMBSTONE,
1296                         .node           = WREPL_NODE_B,
1297                         .is_static      = False,
1298                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1299                         .ips            = addresses_B_1,
1300                         .apply_expected = True
1301                 }
1302         },
1303
1304         /* 
1305          * unique,tombstone vs. unique,active
1306          * => should be replaced
1307          */
1308         {
1309                 .line   = __location__,
1310                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1311                 .r1     = {
1312                         .owner          = &ctx->b,
1313                         .type           = WREPL_TYPE_UNIQUE,
1314                         .state          = WREPL_STATE_TOMBSTONE,
1315                         .node           = WREPL_NODE_B,
1316                         .is_static      = False,
1317                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1318                         .ips            = addresses_B_1,
1319                         .apply_expected = True
1320                 },
1321                 .r2     = {
1322                         .owner          = &ctx->a,
1323                         .type           = WREPL_TYPE_UNIQUE,
1324                         .state          = WREPL_STATE_ACTIVE,
1325                         .node           = WREPL_NODE_B,
1326                         .is_static      = False,
1327                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1328                         .ips            = addresses_A_1,
1329                         .apply_expected = True
1330                 }
1331         },
1332
1333         /* 
1334          * unique,tombstone vs. unique,tombstone
1335          * => should be replaced
1336          */
1337         {
1338                 .line   = __location__,
1339                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1340                 .r1     = {
1341                         .owner          = &ctx->a,
1342                         .type           = WREPL_TYPE_UNIQUE,
1343                         .state          = WREPL_STATE_TOMBSTONE,
1344                         .node           = WREPL_NODE_B,
1345                         .is_static      = False,
1346                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1347                         .ips            = addresses_A_1,
1348                         .apply_expected = True
1349                 },
1350                 .r2     = {
1351                         .owner          = &ctx->b,
1352                         .type           = WREPL_TYPE_UNIQUE,
1353                         .state          = WREPL_STATE_TOMBSTONE,
1354                         .node           = WREPL_NODE_B,
1355                         .is_static      = False,
1356                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1357                         .ips            = addresses_B_1,
1358                         .apply_expected = True
1359                 }
1360         },
1361
1362
1363 /*
1364  * unique vs normal groups section,
1365  */
1366         /* 
1367          * unique,active vs. group,active
1368          * => should be replaced
1369          */
1370         {
1371                 .line   = __location__,
1372                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1373                 .r1     = {
1374                         .owner          = &ctx->b,
1375                         .type           = WREPL_TYPE_UNIQUE,
1376                         .state          = WREPL_STATE_ACTIVE,
1377                         .node           = WREPL_NODE_B,
1378                         .is_static      = False,
1379                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1380                         .ips            = addresses_B_1,
1381                         .apply_expected = True
1382                 },
1383                 .r2     = {
1384                         .owner          = &ctx->a,
1385                         .type           = WREPL_TYPE_GROUP,
1386                         .state          = WREPL_STATE_ACTIVE,
1387                         .node           = WREPL_NODE_B,
1388                         .is_static      = False,
1389                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1390                         .ips            = addresses_A_1,
1391                         .apply_expected = True
1392                 }
1393         },
1394
1395         /* 
1396          * unique,active vs. group,tombstone
1397          * => should NOT be replaced
1398          */
1399         {
1400                 .line   = __location__,
1401                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1402                 .r1     = {
1403                         .owner          = &ctx->a,
1404                         .type           = WREPL_TYPE_UNIQUE,
1405                         .state          = WREPL_STATE_ACTIVE,
1406                         .node           = WREPL_NODE_B,
1407                         .is_static      = False,
1408                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1409                         .ips            = addresses_A_1,
1410                         .apply_expected = True
1411                 },
1412                 .r2     = {
1413                         .owner          = &ctx->b,
1414                         .type           = WREPL_TYPE_GROUP,
1415                         .state          = WREPL_STATE_TOMBSTONE,
1416                         .node           = WREPL_NODE_B,
1417                         .is_static      = False,
1418                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1419                         .ips            = addresses_A_1,
1420                         .apply_expected = False
1421                 }
1422         },
1423
1424         /* 
1425          * unique,released vs. group,active
1426          * => should be replaced
1427          */
1428         {
1429                 .line   = __location__,
1430                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1431                 .r1     = {
1432                         .owner          = &ctx->a,
1433                         .type           = WREPL_TYPE_UNIQUE,
1434                         .state          = WREPL_STATE_RELEASED,
1435                         .node           = WREPL_NODE_B,
1436                         .is_static      = False,
1437                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1438                         .ips            = addresses_A_1,
1439                         .apply_expected = False
1440                 },
1441                 .r2     = {
1442                         .owner          = &ctx->b,
1443                         .type           = WREPL_TYPE_GROUP,
1444                         .state          = WREPL_STATE_ACTIVE,
1445                         .node           = WREPL_NODE_B,
1446                         .is_static      = False,
1447                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1448                         .ips            = addresses_B_1,
1449                         .apply_expected = True
1450                 }
1451         },
1452
1453         /* 
1454          * unique,released vs. group,tombstone
1455          * => should be replaced
1456          */
1457         {
1458                 .line   = __location__,
1459                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1460                 .r1     = {
1461                         .owner          = &ctx->b,
1462                         .type           = WREPL_TYPE_UNIQUE,
1463                         .state          = WREPL_STATE_RELEASED,
1464                         .node           = WREPL_NODE_B,
1465                         .is_static      = False,
1466                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1467                         .ips            = addresses_B_1,
1468                         .apply_expected = False
1469                 },
1470                 .r2     = {
1471                         .owner          = &ctx->a,
1472                         .type           = WREPL_TYPE_GROUP,
1473                         .state          = WREPL_STATE_TOMBSTONE,
1474                         .node           = WREPL_NODE_B,
1475                         .is_static      = False,
1476                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1477                         .ips            = addresses_A_1,
1478                         .apply_expected = True
1479                 }
1480         },
1481
1482         /* 
1483          * unique,tombstone vs. group,active
1484          * => should be replaced
1485          */
1486         {
1487                 .line   = __location__,
1488                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1489                 .r1     = {
1490                         .owner          = &ctx->a,
1491                         .type           = WREPL_TYPE_UNIQUE,
1492                         .state          = WREPL_STATE_TOMBSTONE,
1493                         .node           = WREPL_NODE_B,
1494                         .is_static      = False,
1495                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1496                         .ips            = addresses_A_1,
1497                         .apply_expected = True
1498                 },
1499                 .r2     = {
1500                         .owner          = &ctx->b,
1501                         .type           = WREPL_TYPE_GROUP,
1502                         .state          = WREPL_STATE_ACTIVE,
1503                         .node           = WREPL_NODE_B,
1504                         .is_static      = False,
1505                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1506                         .ips            = addresses_B_1,
1507                         .apply_expected = True
1508                 }
1509         },
1510
1511         /* 
1512          * unique,tombstone vs. group,tombstone
1513          * => should be replaced
1514          */
1515         {
1516                 .line   = __location__,
1517                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1518                 .r1     = {
1519                         .owner          = &ctx->b,
1520                         .type           = WREPL_TYPE_UNIQUE,
1521                         .state          = WREPL_STATE_TOMBSTONE,
1522                         .node           = WREPL_NODE_B,
1523                         .is_static      = False,
1524                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1525                         .ips            = addresses_B_1,
1526                         .apply_expected = True
1527                 },
1528                 .r2     = {
1529                         .owner          = &ctx->a,
1530                         .type           = WREPL_TYPE_GROUP,
1531                         .state          = WREPL_STATE_TOMBSTONE,
1532                         .node           = WREPL_NODE_B,
1533                         .is_static      = False,
1534                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1535                         .ips            = addresses_A_1,
1536                         .apply_expected = True
1537                 }
1538         },
1539
1540 /*
1541  * unique vs special groups section,
1542  */
1543         /* 
1544          * unique,active vs. sgroup,active
1545          * => should NOT be replaced
1546          */
1547         {
1548                 .line   = __location__,
1549                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1550                 .r1     = {
1551                         .owner          = &ctx->a,
1552                         .type           = WREPL_TYPE_UNIQUE,
1553                         .state          = WREPL_STATE_ACTIVE,
1554                         .node           = WREPL_NODE_B,
1555                         .is_static      = False,
1556                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1557                         .ips            = addresses_A_1,
1558                         .apply_expected = True
1559                 },
1560                 .r2     = {
1561                         .owner          = &ctx->b,
1562                         .type           = WREPL_TYPE_SGROUP,
1563                         .state          = WREPL_STATE_ACTIVE,
1564                         .node           = WREPL_NODE_B,
1565                         .is_static      = False,
1566                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1567                         .ips            = addresses_A_1,
1568                         .apply_expected = False
1569                 }
1570         },
1571
1572         /* 
1573          * unique,active vs. sgroup,tombstone
1574          * => should NOT be replaced
1575          */
1576         {
1577                 .line   = __location__,
1578                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1579                 .r1     = {
1580                         .owner          = &ctx->a,
1581                         .type           = WREPL_TYPE_UNIQUE,
1582                         .state          = WREPL_STATE_ACTIVE,
1583                         .node           = WREPL_NODE_B,
1584                         .is_static      = False,
1585                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1586                         .ips            = addresses_A_1,
1587                         .apply_expected = True
1588                 },
1589                 .r2     = {
1590                         .owner          = &ctx->b,
1591                         .type           = WREPL_TYPE_SGROUP,
1592                         .state          = WREPL_STATE_TOMBSTONE,
1593                         .node           = WREPL_NODE_B,
1594                         .is_static      = False,
1595                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1596                         .ips            = addresses_A_1,
1597                         .apply_expected = False
1598                 }
1599         },
1600
1601         /* 
1602          * unique,released vs. sgroup,active
1603          * => should be replaced
1604          */
1605         {
1606                 .line   = __location__,
1607                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1608                 .r1     = {
1609                         .owner          = &ctx->a,
1610                         .type           = WREPL_TYPE_UNIQUE,
1611                         .state          = WREPL_STATE_RELEASED,
1612                         .node           = WREPL_NODE_B,
1613                         .is_static      = False,
1614                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1615                         .ips            = addresses_A_1,
1616                         .apply_expected = False
1617                 },
1618                 .r2     = {
1619                         .owner          = &ctx->b,
1620                         .type           = WREPL_TYPE_SGROUP,
1621                         .state          = WREPL_STATE_ACTIVE,
1622                         .node           = WREPL_NODE_B,
1623                         .is_static      = False,
1624                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1625                         .ips            = addresses_B_3_4,
1626                         .apply_expected = True
1627                 }
1628         },
1629
1630         /* 
1631          * unique,released vs. sgroup,tombstone
1632          * => should be replaced
1633          */
1634         {
1635                 .line   = __location__,
1636                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1637                 .r1     = {
1638                         .owner          = &ctx->b,
1639                         .type           = WREPL_TYPE_UNIQUE,
1640                         .state          = WREPL_STATE_RELEASED,
1641                         .node           = WREPL_NODE_B,
1642                         .is_static      = False,
1643                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1644                         .ips            = addresses_B_1,
1645                         .apply_expected = False
1646                 },
1647                 .r2     = {
1648                         .owner          = &ctx->a,
1649                         .type           = WREPL_TYPE_SGROUP,
1650                         .state          = WREPL_STATE_TOMBSTONE,
1651                         .node           = WREPL_NODE_B,
1652                         .is_static      = False,
1653                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
1654                         .ips            = addresses_A_3_4,
1655                         .apply_expected = True
1656                 }
1657         },
1658
1659         /* 
1660          * unique,tombstone vs. sgroup,active
1661          * => should be replaced
1662          */
1663         {
1664                 .line   = __location__,
1665                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1666                 .r1     = {
1667                         .owner          = &ctx->a,
1668                         .type           = WREPL_TYPE_UNIQUE,
1669                         .state          = WREPL_STATE_TOMBSTONE,
1670                         .node           = WREPL_NODE_B,
1671                         .is_static      = False,
1672                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1673                         .ips            = addresses_A_1,
1674                         .apply_expected = True
1675                 },
1676                 .r2     = {
1677                         .owner          = &ctx->b,
1678                         .type           = WREPL_TYPE_SGROUP,
1679                         .state          = WREPL_STATE_ACTIVE,
1680                         .node           = WREPL_NODE_B,
1681                         .is_static      = False,
1682                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1683                         .ips            = addresses_B_3_4,
1684                         .apply_expected = True
1685                 }
1686         },
1687
1688         /* 
1689          * unique,tombstone vs. sgroup,tombstone
1690          * => should be replaced
1691          */
1692         {
1693                 .line   = __location__,
1694                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1695                 .r1     = {
1696                         .owner          = &ctx->b,
1697                         .type           = WREPL_TYPE_UNIQUE,
1698                         .state          = WREPL_STATE_TOMBSTONE,
1699                         .node           = WREPL_NODE_B,
1700                         .is_static      = False,
1701                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1702                         .ips            = addresses_B_1,
1703                         .apply_expected = True
1704                 },
1705                 .r2     = {
1706                         .owner          = &ctx->a,
1707                         .type           = WREPL_TYPE_SGROUP,
1708                         .state          = WREPL_STATE_TOMBSTONE,
1709                         .node           = WREPL_NODE_B,
1710                         .is_static      = False,
1711                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
1712                         .ips            = addresses_A_3_4,
1713                         .apply_expected = True
1714                 }
1715         },
1716
1717 /*
1718  * unique vs multi homed section,
1719  */
1720         /* 
1721          * unique,active vs. mhomed,active
1722          * => should be replaced
1723          */
1724         {
1725                 .line   = __location__,
1726                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1727                 .r1     = {
1728                         .owner          = &ctx->a,
1729                         .type           = WREPL_TYPE_UNIQUE,
1730                         .state          = WREPL_STATE_ACTIVE,
1731                         .node           = WREPL_NODE_B,
1732                         .is_static      = False,
1733                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1734                         .ips            = addresses_A_1,
1735                         .apply_expected = True
1736                 },
1737                 .r2     = {
1738                         .owner          = &ctx->b,
1739                         .type           = WREPL_TYPE_MHOMED,
1740                         .state          = WREPL_STATE_ACTIVE,
1741                         .node           = WREPL_NODE_B,
1742                         .is_static      = False,
1743                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1744                         .ips            = addresses_B_3_4,
1745                         .apply_expected = True
1746                 }
1747         },
1748
1749         /* 
1750          * unique,active vs. mhomed,tombstone
1751          * => should NOT be replaced
1752          */
1753         {
1754                 .line   = __location__,
1755                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1756                 .r1     = {
1757                         .owner          = &ctx->b,
1758                         .type           = WREPL_TYPE_UNIQUE,
1759                         .state          = WREPL_STATE_ACTIVE,
1760                         .node           = WREPL_NODE_B,
1761                         .is_static      = False,
1762                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1763                         .ips            = addresses_B_3_4,
1764                         .apply_expected = True
1765                 },
1766                 .r2     = {
1767                         .owner          = &ctx->a,
1768                         .type           = WREPL_TYPE_MHOMED,
1769                         .state          = WREPL_STATE_TOMBSTONE,
1770                         .node           = WREPL_NODE_B,
1771                         .is_static      = False,
1772                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1773                         .ips            = addresses_B_3_4,
1774                         .apply_expected = False
1775                 }
1776         },
1777
1778         /* 
1779          * unique,released vs. mhomed,active
1780          * => should be replaced
1781          */
1782         {
1783                 .line   = __location__,
1784                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1785                 .r1     = {
1786                         .owner          = &ctx->b,
1787                         .type           = WREPL_TYPE_UNIQUE,
1788                         .state          = WREPL_STATE_RELEASED,
1789                         .node           = WREPL_NODE_B,
1790                         .is_static      = False,
1791                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1792                         .ips            = addresses_B_1,
1793                         .apply_expected = False
1794                 },
1795                 .r2     = {
1796                         .owner          = &ctx->a,
1797                         .type           = WREPL_TYPE_MHOMED,
1798                         .state          = WREPL_STATE_ACTIVE,
1799                         .node           = WREPL_NODE_B,
1800                         .is_static      = False,
1801                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
1802                         .ips            = addresses_A_3_4,
1803                         .apply_expected = True
1804                 }
1805         },
1806
1807         /* 
1808          * unique,released vs. mhomed,tombstone
1809          * => should be replaced
1810          */
1811         {
1812                 .line   = __location__,
1813                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1814                 .r1     = {
1815                         .owner          = &ctx->a,
1816                         .type           = WREPL_TYPE_UNIQUE,
1817                         .state          = WREPL_STATE_RELEASED,
1818                         .node           = WREPL_NODE_B,
1819                         .is_static      = False,
1820                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1821                         .ips            = addresses_A_1,
1822                         .apply_expected = False
1823                 },
1824                 .r2     = {
1825                         .owner          = &ctx->b,
1826                         .type           = WREPL_TYPE_MHOMED,
1827                         .state          = WREPL_STATE_TOMBSTONE,
1828                         .node           = WREPL_NODE_B,
1829                         .is_static      = False,
1830                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1831                         .ips            = addresses_B_3_4,
1832                         .apply_expected = True
1833                 }
1834         },
1835
1836         /* 
1837          * unique,tombstone vs. mhomed,active
1838          * => should be replaced
1839          */
1840         {
1841                 .line   = __location__,
1842                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1843                 .r1     = {
1844                         .owner          = &ctx->b,
1845                         .type           = WREPL_TYPE_UNIQUE,
1846                         .state          = WREPL_STATE_TOMBSTONE,
1847                         .node           = WREPL_NODE_B,
1848                         .is_static      = False,
1849                         .num_ips        = ARRAY_SIZE(addresses_B_1),
1850                         .ips            = addresses_B_1,
1851                         .apply_expected = True
1852                 },
1853                 .r2     = {
1854                         .owner          = &ctx->a,
1855                         .type           = WREPL_TYPE_MHOMED,
1856                         .state          = WREPL_STATE_ACTIVE,
1857                         .node           = WREPL_NODE_B,
1858                         .is_static      = False,
1859                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
1860                         .ips            = addresses_A_3_4,
1861                         .apply_expected = True
1862                 }
1863         },
1864
1865         /* 
1866          * unique,tombstone vs. mhomed,tombstone
1867          * => should be replaced
1868          */
1869         {
1870                 .line   = __location__,
1871                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1872                 .r1     = {
1873                         .owner          = &ctx->a,
1874                         .type           = WREPL_TYPE_UNIQUE,
1875                         .state          = WREPL_STATE_TOMBSTONE,
1876                         .node           = WREPL_NODE_B,
1877                         .is_static      = False,
1878                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1879                         .ips            = addresses_A_1,
1880                         .apply_expected = True
1881                 },
1882                 .r2     = {
1883                         .owner          = &ctx->b,
1884                         .type           = WREPL_TYPE_MHOMED,
1885                         .state          = WREPL_STATE_TOMBSTONE,
1886                         .node           = WREPL_NODE_B,
1887                         .is_static      = False,
1888                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
1889                         .ips            = addresses_B_3_4,
1890                         .apply_expected = True
1891                 }
1892         },
1893
1894 /*
1895  * normal groups vs unique section,
1896  */
1897         /* 
1898          * group,active vs. unique,active
1899          * => should NOT be replaced
1900          */
1901         {
1902                 .line   = __location__,
1903                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1904                 .r1     = {
1905                         .owner          = &ctx->a,
1906                         .type           = WREPL_TYPE_GROUP,
1907                         .state          = WREPL_STATE_ACTIVE,
1908                         .node           = WREPL_NODE_B,
1909                         .is_static      = False,
1910                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1911                         .ips            = addresses_A_1,
1912                         .apply_expected = True
1913                 },
1914                 .r2     = {
1915                         .owner          = &ctx->b,
1916                         .type           = WREPL_TYPE_UNIQUE,
1917                         .state          = WREPL_STATE_ACTIVE,
1918                         .node           = WREPL_NODE_B,
1919                         .is_static      = False,
1920                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1921                         .ips            = addresses_A_1,
1922                         .apply_expected = False
1923                 }
1924         },
1925
1926         /* 
1927          * group,active vs. unique,tombstone
1928          * => should NOT be replaced
1929          */
1930         {
1931                 .line   = __location__,
1932                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1933                 .r1     = {
1934                         .owner          = &ctx->a,
1935                         .type           = WREPL_TYPE_GROUP,
1936                         .state          = WREPL_STATE_ACTIVE,
1937                         .node           = WREPL_NODE_B,
1938                         .is_static      = False,
1939                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1940                         .ips            = addresses_A_1,
1941                         .apply_expected = True
1942                 },
1943                 .r2     = {
1944                         .owner          = &ctx->b,
1945                         .type           = WREPL_TYPE_UNIQUE,
1946                         .state          = WREPL_STATE_TOMBSTONE,
1947                         .node           = WREPL_NODE_B,
1948                         .is_static      = False,
1949                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1950                         .ips            = addresses_A_1,
1951                         .apply_expected = False
1952                 }
1953         },
1954
1955         /* 
1956          * group,released vs. unique,active
1957          * => should NOT be replaced
1958          */
1959         {
1960                 .line   = __location__,
1961                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1962                 .r1     = {
1963                         .owner          = &ctx->a,
1964                         .type           = WREPL_TYPE_GROUP,
1965                         .state          = WREPL_STATE_RELEASED,
1966                         .node           = WREPL_NODE_B,
1967                         .is_static      = False,
1968                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1969                         .ips            = addresses_A_1,
1970                         .apply_expected = False
1971                 },
1972                 .r2     = {
1973                         .owner          = &ctx->b,
1974                         .type           = WREPL_TYPE_UNIQUE,
1975                         .state          = WREPL_STATE_ACTIVE,
1976                         .node           = WREPL_NODE_B,
1977                         .is_static      = False,
1978                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1979                         .ips            = addresses_A_1,
1980                         .apply_expected = False
1981                 }
1982         },
1983
1984         /* 
1985          * group,released vs. unique,tombstone
1986          * => should NOT be replaced
1987          */
1988         {
1989                 .line   = __location__,
1990                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
1991                 .r1     = {
1992                         .owner          = &ctx->a,
1993                         .type           = WREPL_TYPE_GROUP,
1994                         .state          = WREPL_STATE_RELEASED,
1995                         .node           = WREPL_NODE_B,
1996                         .is_static      = False,
1997                         .num_ips        = ARRAY_SIZE(addresses_A_1),
1998                         .ips            = addresses_A_1,
1999                         .apply_expected = False
2000                 },
2001                 .r2     = {
2002                         .owner          = &ctx->b,
2003                         .type           = WREPL_TYPE_UNIQUE,
2004                         .state          = WREPL_STATE_TOMBSTONE,
2005                         .node           = WREPL_NODE_B,
2006                         .is_static      = False,
2007                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2008                         .ips            = addresses_A_1,
2009                         .apply_expected = False
2010                 }
2011         },
2012
2013         /* 
2014          * group,tombstone vs. unique,active
2015          * => should NOT be replaced
2016          */
2017         {
2018                 .line   = __location__,
2019                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2020                 .r1     = {
2021                         .owner          = &ctx->a,
2022                         .type           = WREPL_TYPE_GROUP,
2023                         .state          = WREPL_STATE_TOMBSTONE,
2024                         .node           = WREPL_NODE_B,
2025                         .is_static      = False,
2026                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2027                         .ips            = addresses_A_1,
2028                         .apply_expected = True
2029                 },
2030                 .r2     = {
2031                         .owner          = &ctx->b,
2032                         .type           = WREPL_TYPE_UNIQUE,
2033                         .state          = WREPL_STATE_ACTIVE,
2034                         .node           = WREPL_NODE_B,
2035                         .is_static      = False,
2036                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2037                         .ips            = addresses_A_1,
2038                         .apply_expected = False
2039                 }
2040         },
2041
2042         /* 
2043          * group,tombstone vs. unique,tombstone
2044          * => should NOT be replaced
2045          */
2046         {
2047                 .line   = __location__,
2048                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2049                 .r1     = {
2050                         .owner          = &ctx->a,
2051                         .type           = WREPL_TYPE_GROUP,
2052                         .state          = WREPL_STATE_TOMBSTONE,
2053                         .node           = WREPL_NODE_B,
2054                         .is_static      = False,
2055                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2056                         .ips            = addresses_A_1,
2057                         .apply_expected = True
2058                 },
2059                 .r2     = {
2060                         .owner          = &ctx->b,
2061                         .type           = WREPL_TYPE_UNIQUE,
2062                         .state          = WREPL_STATE_TOMBSTONE,
2063                         .node           = WREPL_NODE_B,
2064                         .is_static      = False,
2065                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2066                         .ips            = addresses_A_1,
2067                         .apply_expected = False
2068                 }
2069         },
2070
2071 /*
2072  * normal groups vs normal groups section,
2073  */
2074         /* 
2075          * group,active vs. group,active
2076          * => should NOT be replaced
2077          */
2078         {
2079                 .line   = __location__,
2080                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2081                 .r1     = {
2082                         .owner          = &ctx->a,
2083                         .type           = WREPL_TYPE_GROUP,
2084                         .state          = WREPL_STATE_ACTIVE,
2085                         .node           = WREPL_NODE_B,
2086                         .is_static      = False,
2087                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2088                         .ips            = addresses_A_1,
2089                         .apply_expected = True
2090                 },
2091                 .r2     = {
2092                         .owner          = &ctx->b,
2093                         .type           = WREPL_TYPE_GROUP,
2094                         .state          = WREPL_STATE_ACTIVE,
2095                         .node           = WREPL_NODE_B,
2096                         .is_static      = False,
2097                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2098                         .ips            = addresses_A_1,
2099                         .apply_expected = False
2100                 }
2101         },
2102
2103         /* 
2104          * group,active vs. group,tombstone
2105          * => should NOT be replaced
2106          */
2107         {
2108                 .line   = __location__,
2109                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2110                 .r1     = {
2111                         .owner          = &ctx->a,
2112                         .type           = WREPL_TYPE_GROUP,
2113                         .state          = WREPL_STATE_ACTIVE,
2114                         .node           = WREPL_NODE_B,
2115                         .is_static      = False,
2116                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2117                         .ips            = addresses_A_1,
2118                         .apply_expected = True
2119                 },
2120                 .r2     = {
2121                         .owner          = &ctx->b,
2122                         .type           = WREPL_TYPE_GROUP,
2123                         .state          = WREPL_STATE_TOMBSTONE,
2124                         .node           = WREPL_NODE_B,
2125                         .is_static      = False,
2126                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2127                         .ips            = addresses_A_1,
2128                         .apply_expected = False
2129                 }
2130         },
2131
2132         /* 
2133          * group,released vs. group,active
2134          * => should be replaced
2135          */
2136         {
2137                 .line   = __location__,
2138                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2139                 .r1     = {
2140                         .owner          = &ctx->a,
2141                         .type           = WREPL_TYPE_GROUP,
2142                         .state          = WREPL_STATE_RELEASED,
2143                         .node           = WREPL_NODE_B,
2144                         .is_static      = False,
2145                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2146                         .ips            = addresses_A_1,
2147                         .apply_expected = False
2148                 },
2149                 .r2     = {
2150                         .owner          = &ctx->b,
2151                         .type           = WREPL_TYPE_GROUP,
2152                         .state          = WREPL_STATE_ACTIVE,
2153                         .node           = WREPL_NODE_B,
2154                         .is_static      = False,
2155                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2156                         .ips            = addresses_B_1,
2157                         .apply_expected = True
2158                 }
2159         },
2160
2161         /* 
2162          * group,released vs. group,tombstone
2163          * => should be replaced
2164          */
2165         {
2166                 .line   = __location__,
2167                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2168                 .r1     = {
2169                         .owner          = &ctx->a,
2170                         .type           = WREPL_TYPE_GROUP,
2171                         .state          = WREPL_STATE_RELEASED,
2172                         .node           = WREPL_NODE_B,
2173                         .is_static      = False,
2174                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2175                         .ips            = addresses_A_1,
2176                         .apply_expected = False
2177                 },
2178                 .r2     = {
2179                         .owner          = &ctx->b,
2180                         .type           = WREPL_TYPE_GROUP,
2181                         .state          = WREPL_STATE_TOMBSTONE,
2182                         .node           = WREPL_NODE_B,
2183                         .is_static      = False,
2184                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2185                         .ips            = addresses_B_1,
2186                         .apply_expected = True
2187                 }
2188         },
2189
2190         /* 
2191          * group,tombstone vs. group,active
2192          * => should be replaced
2193          */
2194         {
2195                 .line   = __location__,
2196                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2197                 .r1     = {
2198                         .owner          = &ctx->b,
2199                         .type           = WREPL_TYPE_GROUP,
2200                         .state          = WREPL_STATE_TOMBSTONE,
2201                         .node           = WREPL_NODE_B,
2202                         .is_static      = False,
2203                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2204                         .ips            = addresses_B_1,
2205                         .apply_expected = True
2206                 },
2207                 .r2     = {
2208                         .owner          = &ctx->a,
2209                         .type           = WREPL_TYPE_GROUP,
2210                         .state          = WREPL_STATE_ACTIVE,
2211                         .node           = WREPL_NODE_B,
2212                         .is_static      = False,
2213                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2214                         .ips            = addresses_A_1,
2215                         .apply_expected = True
2216                 }
2217         },
2218
2219         /* 
2220          * group,tombstone vs. group,tombstone
2221          * => should be replaced
2222          */
2223         {
2224                 .line   = __location__,
2225                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2226                 .r1     = {
2227                         .owner          = &ctx->a,
2228                         .type           = WREPL_TYPE_GROUP,
2229                         .state          = WREPL_STATE_TOMBSTONE,
2230                         .node           = WREPL_NODE_B,
2231                         .is_static      = False,
2232                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2233                         .ips            = addresses_A_1,
2234                         .apply_expected = True
2235                 },
2236                 .r2     = {
2237                         .owner          = &ctx->b,
2238                         .type           = WREPL_TYPE_GROUP,
2239                         .state          = WREPL_STATE_TOMBSTONE,
2240                         .node           = WREPL_NODE_B,
2241                         .is_static      = False,
2242                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2243                         .ips            = addresses_B_1,
2244                         .apply_expected = True
2245                 }
2246         },
2247
2248 /*
2249  * normal groups vs special groups section,
2250  */
2251         /* 
2252          * group,active vs. sgroup,active
2253          * => should NOT be replaced
2254          */
2255         {
2256                 .line   = __location__,
2257                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2258                 .r1     = {
2259                         .owner          = &ctx->b,
2260                         .type           = WREPL_TYPE_GROUP,
2261                         .state          = WREPL_STATE_ACTIVE,
2262                         .node           = WREPL_NODE_B,
2263                         .is_static      = False,
2264                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2265                         .ips            = addresses_B_1,
2266                         .apply_expected = True
2267                 },
2268                 .r2     = {
2269                         .owner          = &ctx->a,
2270                         .type           = WREPL_TYPE_SGROUP,
2271                         .state          = WREPL_STATE_ACTIVE,
2272                         .node           = WREPL_NODE_B,
2273                         .is_static      = False,
2274                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2275                         .ips            = addresses_B_1,
2276                         .apply_expected = False
2277                 }
2278         },
2279
2280         /* 
2281          * group,active vs. sgroup,tombstone
2282          * => should NOT be replaced
2283          */
2284         {
2285                 .line   = __location__,
2286                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2287                 .r1     = {
2288                         .owner          = &ctx->b,
2289                         .type           = WREPL_TYPE_GROUP,
2290                         .state          = WREPL_STATE_ACTIVE,
2291                         .node           = WREPL_NODE_B,
2292                         .is_static      = False,
2293                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2294                         .ips            = addresses_B_1,
2295                         .apply_expected = True
2296                 },
2297                 .r2     = {
2298                         .owner          = &ctx->a,
2299                         .type           = WREPL_TYPE_SGROUP,
2300                         .state          = WREPL_STATE_TOMBSTONE,
2301                         .node           = WREPL_NODE_B,
2302                         .is_static      = False,
2303                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2304                         .ips            = addresses_B_1,
2305                         .apply_expected = False
2306                 }
2307         },
2308
2309         /* 
2310          * group,released vs. sgroup,active
2311          * => should be replaced
2312          */
2313         {
2314                 .line   = __location__,
2315                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2316                 .r1     = {
2317                         .owner          = &ctx->a,
2318                         .type           = WREPL_TYPE_GROUP,
2319                         .state          = WREPL_STATE_RELEASED,
2320                         .node           = WREPL_NODE_B,
2321                         .is_static      = False,
2322                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2323                         .ips            = addresses_A_1,
2324                         .apply_expected = False
2325                 },
2326                 .r2     = {
2327                         .owner          = &ctx->b,
2328                         .type           = WREPL_TYPE_SGROUP,
2329                         .state          = WREPL_STATE_ACTIVE,
2330                         .node           = WREPL_NODE_B,
2331                         .is_static      = False,
2332                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2333                         .ips            = addresses_B_1,
2334                         .apply_expected = True
2335                 }
2336         },
2337
2338         /* 
2339          * group,released vs. sgroup,tombstone
2340          * => should NOT be replaced
2341          */
2342         {
2343                 .line   = __location__,
2344                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2345                 .r1     = {
2346                         .owner          = &ctx->b,
2347                         .type           = WREPL_TYPE_GROUP,
2348                         .state          = WREPL_STATE_RELEASED,
2349                         .node           = WREPL_NODE_B,
2350                         .is_static      = False,
2351                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2352                         .ips            = addresses_B_1,
2353                         .apply_expected = False
2354                 },
2355                 .r2     = {
2356                         .owner          = &ctx->a,
2357                         .type           = WREPL_TYPE_SGROUP,
2358                         .state          = WREPL_STATE_TOMBSTONE,
2359                         .node           = WREPL_NODE_B,
2360                         .is_static      = False,
2361                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2362                         .ips            = addresses_B_1,
2363                         .apply_expected = False
2364                 }
2365         },
2366
2367         /* 
2368          * group,tombstone vs. sgroup,active
2369          * => should be replaced
2370          */
2371         {
2372                 .line   = __location__,
2373                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2374                 .r1     = {
2375                         .owner          = &ctx->b,
2376                         .type           = WREPL_TYPE_GROUP,
2377                         .state          = WREPL_STATE_TOMBSTONE,
2378                         .node           = WREPL_NODE_B,
2379                         .is_static      = False,
2380                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2381                         .ips            = addresses_B_1,
2382                         .apply_expected = True
2383                 },
2384                 .r2     = {
2385                         .owner          = &ctx->a,
2386                         .type           = WREPL_TYPE_SGROUP,
2387                         .state          = WREPL_STATE_ACTIVE,
2388                         .node           = WREPL_NODE_B,
2389                         .is_static      = False,
2390                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2391                         .ips            = addresses_A_1,
2392                         .apply_expected = True
2393                 }
2394         },
2395
2396         /* 
2397          * group,tombstone vs. sgroup,tombstone
2398          * => should be replaced
2399          */
2400         {
2401                 .line   = __location__,
2402                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2403                 .r1     = {
2404                         .owner          = &ctx->a,
2405                         .type           = WREPL_TYPE_GROUP,
2406                         .state          = WREPL_STATE_TOMBSTONE,
2407                         .node           = WREPL_NODE_B,
2408                         .is_static      = False,
2409                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2410                         .ips            = addresses_A_1,
2411                         .apply_expected = True
2412                 },
2413                 .r2     = {
2414                         .owner          = &ctx->b,
2415                         .type           = WREPL_TYPE_SGROUP,
2416                         .state          = WREPL_STATE_TOMBSTONE,
2417                         .node           = WREPL_NODE_B,
2418                         .is_static      = False,
2419                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2420                         .ips            = addresses_B_1,
2421                         .apply_expected = True
2422                 }
2423         },
2424
2425 /*
2426  * normal groups vs multi homed section,
2427  */
2428         /* 
2429          * group,active vs. mhomed,active
2430          * => should NOT be replaced
2431          */
2432         {
2433                 .line   = __location__,
2434                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2435                 .r1     = {
2436                         .owner          = &ctx->b,
2437                         .type           = WREPL_TYPE_GROUP,
2438                         .state          = WREPL_STATE_ACTIVE,
2439                         .node           = WREPL_NODE_B,
2440                         .is_static      = False,
2441                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2442                         .ips            = addresses_B_1,
2443                         .apply_expected = True
2444                 },
2445                 .r2     = {
2446                         .owner          = &ctx->a,
2447                         .type           = WREPL_TYPE_MHOMED,
2448                         .state          = WREPL_STATE_ACTIVE,
2449                         .node           = WREPL_NODE_B,
2450                         .is_static      = False,
2451                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2452                         .ips            = addresses_B_1,
2453                         .apply_expected = False
2454                 }
2455         },
2456
2457         /* 
2458          * group,active vs. mhomed,tombstone
2459          * => should NOT be replaced
2460          */
2461         {
2462                 .line   = __location__,
2463                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2464                 .r1     = {
2465                         .owner          = &ctx->b,
2466                         .type           = WREPL_TYPE_GROUP,
2467                         .state          = WREPL_STATE_ACTIVE,
2468                         .node           = WREPL_NODE_B,
2469                         .is_static      = False,
2470                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2471                         .ips            = addresses_B_1,
2472                         .apply_expected = True
2473                 },
2474                 .r2     = {
2475                         .owner          = &ctx->a,
2476                         .type           = WREPL_TYPE_MHOMED,
2477                         .state          = WREPL_STATE_TOMBSTONE,
2478                         .node           = WREPL_NODE_B,
2479                         .is_static      = False,
2480                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2481                         .ips            = addresses_B_1,
2482                         .apply_expected = False
2483                 }
2484         },
2485
2486         /* 
2487          * group,released vs. mhomed,active
2488          * => should NOT be replaced
2489          */
2490         {
2491                 .line   = __location__,
2492                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2493                 .r1     = {
2494                         .owner          = &ctx->b,
2495                         .type           = WREPL_TYPE_GROUP,
2496                         .state          = WREPL_STATE_RELEASED,
2497                         .node           = WREPL_NODE_B,
2498                         .is_static      = False,
2499                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2500                         .ips            = addresses_B_1,
2501                         .apply_expected = False
2502                 },
2503                 .r2     = {
2504                         .owner          = &ctx->a,
2505                         .type           = WREPL_TYPE_MHOMED,
2506                         .state          = WREPL_STATE_ACTIVE,
2507                         .node           = WREPL_NODE_B,
2508                         .is_static      = False,
2509                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2510                         .ips            = addresses_B_1,
2511                         .apply_expected = False
2512                 }
2513         },
2514
2515         /* 
2516          * group,released vs. mhomed,tombstone
2517          * => should NOT be replaced
2518          */
2519         {
2520                 .line   = __location__,
2521                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2522                 .r1     = {
2523                         .owner          = &ctx->b,
2524                         .type           = WREPL_TYPE_GROUP,
2525                         .state          = WREPL_STATE_RELEASED,
2526                         .node           = WREPL_NODE_B,
2527                         .is_static      = False,
2528                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2529                         .ips            = addresses_B_1,
2530                         .apply_expected = False
2531                 },
2532                 .r2     = {
2533                         .owner          = &ctx->a,
2534                         .type           = WREPL_TYPE_MHOMED,
2535                         .state          = WREPL_STATE_TOMBSTONE,
2536                         .node           = WREPL_NODE_B,
2537                         .is_static      = False,
2538                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2539                         .ips            = addresses_B_1,
2540                         .apply_expected = False
2541                 }
2542         },
2543
2544         /* 
2545          * group,tombstone vs. mhomed,active
2546          * => should be replaced
2547          */
2548         {
2549                 .line   = __location__,
2550                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2551                 .r1     = {
2552                         .owner          = &ctx->b,
2553                         .type           = WREPL_TYPE_GROUP,
2554                         .state          = WREPL_STATE_TOMBSTONE,
2555                         .node           = WREPL_NODE_B,
2556                         .is_static      = False,
2557                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2558                         .ips            = addresses_B_1,
2559                         .apply_expected = True
2560                 },
2561                 .r2     = {
2562                         .owner          = &ctx->a,
2563                         .type           = WREPL_TYPE_MHOMED,
2564                         .state          = WREPL_STATE_ACTIVE,
2565                         .node           = WREPL_NODE_B,
2566                         .is_static      = False,
2567                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2568                         .ips            = addresses_A_1,
2569                         .apply_expected = True
2570                 }
2571         },
2572
2573         /* 
2574          * group,tombstone vs. mhomed,tombstone
2575          * => should be replaced
2576          */
2577         {
2578                 .line   = __location__,
2579                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2580                 .r1     = {
2581                         .owner          = &ctx->a,
2582                         .type           = WREPL_TYPE_GROUP,
2583                         .state          = WREPL_STATE_TOMBSTONE,
2584                         .node           = WREPL_NODE_B,
2585                         .is_static      = False,
2586                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2587                         .ips            = addresses_A_1,
2588                         .apply_expected = True
2589                 },
2590                 .r2     = {
2591                         .owner          = &ctx->b,
2592                         .type           = WREPL_TYPE_MHOMED,
2593                         .state          = WREPL_STATE_TOMBSTONE,
2594                         .node           = WREPL_NODE_B,
2595                         .is_static      = False,
2596                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2597                         .ips            = addresses_B_1,
2598                         .apply_expected = True
2599                 }
2600         },
2601
2602 /*
2603  * special groups vs unique section,
2604  */
2605         /* 
2606          * sgroup,active vs. unique,active
2607          * => should NOT be replaced
2608          */
2609         {
2610                 .line   = __location__,
2611                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2612                 .r1     = {
2613                         .owner          = &ctx->b,
2614                         .type           = WREPL_TYPE_SGROUP,
2615                         .state          = WREPL_STATE_ACTIVE,
2616                         .node           = WREPL_NODE_B,
2617                         .is_static      = False,
2618                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2619                         .ips            = addresses_B_1,
2620                         .apply_expected = True
2621                 },
2622                 .r2     = {
2623                         .owner          = &ctx->a,
2624                         .type           = WREPL_TYPE_UNIQUE,
2625                         .state          = WREPL_STATE_ACTIVE,
2626                         .node           = WREPL_NODE_B,
2627                         .is_static      = False,
2628                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2629                         .ips            = addresses_B_1,
2630                         .apply_expected = False
2631                 }
2632         },
2633
2634         /* 
2635          * sgroup,active vs. unique,tombstone
2636          * => should NOT be replaced
2637          */
2638         {
2639                 .line   = __location__,
2640                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2641                 .r1     = {
2642                         .owner          = &ctx->b,
2643                         .type           = WREPL_TYPE_SGROUP,
2644                         .state          = WREPL_STATE_ACTIVE,
2645                         .node           = WREPL_NODE_B,
2646                         .is_static      = False,
2647                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2648                         .ips            = addresses_B_1,
2649                         .apply_expected = True
2650                 },
2651                 .r2     = {
2652                         .owner          = &ctx->a,
2653                         .type           = WREPL_TYPE_UNIQUE,
2654                         .state          = WREPL_STATE_TOMBSTONE,
2655                         .node           = WREPL_NODE_B,
2656                         .is_static      = False,
2657                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2658                         .ips            = addresses_B_1,
2659                         .apply_expected = False
2660                 }
2661         },
2662
2663         /* 
2664          * sgroup,released vs. unique,active
2665          * => should be replaced
2666          */
2667         {
2668                 .line   = __location__,
2669                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2670                 .r1     = {
2671                         .owner          = &ctx->b,
2672                         .type           = WREPL_TYPE_SGROUP,
2673                         .state          = WREPL_STATE_RELEASED,
2674                         .node           = WREPL_NODE_B,
2675                         .is_static      = False,
2676                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2677                         .ips            = addresses_B_1,
2678                         .apply_expected = False
2679                 },
2680                 .r2     = {
2681                         .owner          = &ctx->a,
2682                         .type           = WREPL_TYPE_UNIQUE,
2683                         .state          = WREPL_STATE_ACTIVE,
2684                         .node           = WREPL_NODE_B,
2685                         .is_static      = False,
2686                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2687                         .ips            = addresses_A_1,
2688                         .apply_expected = True
2689                 }
2690         },
2691
2692         /* 
2693          * sgroup,released vs. unique,tombstone
2694          * => should be replaced
2695          */
2696         {
2697                 .line   = __location__,
2698                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2699                 .r1     = {
2700                         .owner          = &ctx->a,
2701                         .type           = WREPL_TYPE_SGROUP,
2702                         .state          = WREPL_STATE_RELEASED,
2703                         .node           = WREPL_NODE_B,
2704                         .is_static      = False,
2705                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2706                         .ips            = addresses_A_1,
2707                         .apply_expected = False
2708                 },
2709                 .r2     = {
2710                         .owner          = &ctx->b,
2711                         .type           = WREPL_TYPE_UNIQUE,
2712                         .state          = WREPL_STATE_TOMBSTONE,
2713                         .node           = WREPL_NODE_B,
2714                         .is_static      = False,
2715                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2716                         .ips            = addresses_B_1,
2717                         .apply_expected = True
2718                 }
2719         },
2720
2721         /* 
2722          * sgroup,tombstone vs. unique,active
2723          * => should be replaced
2724          */
2725         {
2726                 .line   = __location__,
2727                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2728                 .r1     = {
2729                         .owner          = &ctx->a,
2730                         .type           = WREPL_TYPE_SGROUP,
2731                         .state          = WREPL_STATE_TOMBSTONE,
2732                         .node           = WREPL_NODE_B,
2733                         .is_static      = False,
2734                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2735                         .ips            = addresses_A_1,
2736                         .apply_expected = True
2737                 },
2738                 .r2     = {
2739                         .owner          = &ctx->b,
2740                         .type           = WREPL_TYPE_UNIQUE,
2741                         .state          = WREPL_STATE_ACTIVE,
2742                         .node           = WREPL_NODE_B,
2743                         .is_static      = False,
2744                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2745                         .ips            = addresses_B_1,
2746                         .apply_expected = True
2747                 }
2748         },
2749
2750         /* 
2751          * sgroup,tombstone vs. unique,tombstone
2752          * => should be replaced
2753          */
2754         {
2755                 .line   = __location__,
2756                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2757                 .r1     = {
2758                         .owner          = &ctx->b,
2759                         .type           = WREPL_TYPE_SGROUP,
2760                         .state          = WREPL_STATE_TOMBSTONE,
2761                         .node           = WREPL_NODE_B,
2762                         .is_static      = False,
2763                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2764                         .ips            = addresses_B_1,
2765                         .apply_expected = True
2766                 },
2767                 .r2     = {
2768                         .owner          = &ctx->a,
2769                         .type           = WREPL_TYPE_UNIQUE,
2770                         .state          = WREPL_STATE_TOMBSTONE,
2771                         .node           = WREPL_NODE_B,
2772                         .is_static      = False,
2773                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2774                         .ips            = addresses_A_1,
2775                         .apply_expected = True
2776                 }
2777         },
2778
2779 /*
2780  * special groups vs normal group section,
2781  */
2782         /* 
2783          * sgroup,active vs. group,active
2784          * => should NOT be replaced
2785          */
2786         {
2787                 .line   = __location__,
2788                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2789                 .r1     = {
2790                         .owner          = &ctx->a,
2791                         .type           = WREPL_TYPE_SGROUP,
2792                         .state          = WREPL_STATE_ACTIVE,
2793                         .node           = WREPL_NODE_B,
2794                         .is_static      = False,
2795                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2796                         .ips            = addresses_A_1,
2797                         .apply_expected = True
2798                 },
2799                 .r2     = {
2800                         .owner          = &ctx->b,
2801                         .type           = WREPL_TYPE_GROUP,
2802                         .state          = WREPL_STATE_ACTIVE,
2803                         .node           = WREPL_NODE_B,
2804                         .is_static      = False,
2805                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2806                         .ips            = addresses_A_1,
2807                         .apply_expected = False
2808                 }
2809         },
2810
2811         /* 
2812          * sgroup,active vs. group,tombstone
2813          * => should NOT be replaced
2814          */
2815         {
2816                 .line   = __location__,
2817                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2818                 .r1     = {
2819                         .owner          = &ctx->a,
2820                         .type           = WREPL_TYPE_SGROUP,
2821                         .state          = WREPL_STATE_ACTIVE,
2822                         .node           = WREPL_NODE_B,
2823                         .is_static      = False,
2824                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2825                         .ips            = addresses_A_1,
2826                         .apply_expected = True
2827                 },
2828                 .r2     = {
2829                         .owner          = &ctx->b,
2830                         .type           = WREPL_TYPE_GROUP,
2831                         .state          = WREPL_STATE_TOMBSTONE,
2832                         .node           = WREPL_NODE_B,
2833                         .is_static      = False,
2834                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2835                         .ips            = addresses_A_1,
2836                         .apply_expected = False
2837                 }
2838         },
2839
2840         /* 
2841          * sgroup,released vs. group,active
2842          * => should be replaced
2843          */
2844         {
2845                 .line   = __location__,
2846                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2847                 .r1     = {
2848                         .owner          = &ctx->a,
2849                         .type           = WREPL_TYPE_SGROUP,
2850                         .state          = WREPL_STATE_RELEASED,
2851                         .node           = WREPL_NODE_B,
2852                         .is_static      = False,
2853                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2854                         .ips            = addresses_A_1,
2855                         .apply_expected = False
2856                 },
2857                 .r2     = {
2858                         .owner          = &ctx->b,
2859                         .type           = WREPL_TYPE_GROUP,
2860                         .state          = WREPL_STATE_ACTIVE,
2861                         .node           = WREPL_NODE_B,
2862                         .is_static      = False,
2863                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2864                         .ips            = addresses_B_1,
2865                         .apply_expected = True
2866                 }
2867         },
2868
2869         /* 
2870          * sgroup,released vs. group,tombstone
2871          * => should be replaced
2872          */
2873         {
2874                 .line   = __location__,
2875                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2876                 .r1     = {
2877                         .owner          = &ctx->b,
2878                         .type           = WREPL_TYPE_SGROUP,
2879                         .state          = WREPL_STATE_RELEASED,
2880                         .node           = WREPL_NODE_B,
2881                         .is_static      = False,
2882                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2883                         .ips            = addresses_B_1,
2884                         .apply_expected = False
2885                 },
2886                 .r2     = {
2887                         .owner          = &ctx->a,
2888                         .type           = WREPL_TYPE_GROUP,
2889                         .state          = WREPL_STATE_TOMBSTONE,
2890                         .node           = WREPL_NODE_B,
2891                         .is_static      = False,
2892                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2893                         .ips            = addresses_A_1,
2894                         .apply_expected = True
2895                 }
2896         },
2897
2898         /* 
2899          * sgroup,tombstone vs. group,active
2900          * => should NOT be replaced
2901          */
2902         {
2903                 .line   = __location__,
2904                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2905                 .r1     = {
2906                         .owner          = &ctx->a,
2907                         .type           = WREPL_TYPE_SGROUP,
2908                         .state          = WREPL_STATE_TOMBSTONE,
2909                         .node           = WREPL_NODE_B,
2910                         .is_static      = False,
2911                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2912                         .ips            = addresses_A_1,
2913                         .apply_expected = True
2914                 },
2915                 .r2     = {
2916                         .owner          = &ctx->b,
2917                         .type           = WREPL_TYPE_GROUP,
2918                         .state          = WREPL_STATE_ACTIVE,
2919                         .node           = WREPL_NODE_B,
2920                         .is_static      = False,
2921                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2922                         .ips            = addresses_B_1,
2923                         .apply_expected = True
2924                 }
2925         },
2926
2927         /* 
2928          * sgroup,tombstone vs. group,tombstone
2929          * => should NOT be replaced
2930          */
2931         {
2932                 .line   = __location__,
2933                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2934                 .r1     = {
2935                         .owner          = &ctx->b,
2936                         .type           = WREPL_TYPE_SGROUP,
2937                         .state          = WREPL_STATE_TOMBSTONE,
2938                         .node           = WREPL_NODE_B,
2939                         .is_static      = False,
2940                         .num_ips        = ARRAY_SIZE(addresses_B_1),
2941                         .ips            = addresses_B_1,
2942                         .apply_expected = True
2943                 },
2944                 .r2     = {
2945                         .owner          = &ctx->a,
2946                         .type           = WREPL_TYPE_GROUP,
2947                         .state          = WREPL_STATE_TOMBSTONE,
2948                         .node           = WREPL_NODE_B,
2949                         .is_static      = False,
2950                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2951                         .ips            = addresses_A_1,
2952                         .apply_expected = True
2953                 }
2954         },
2955
2956 /*
2957  * special groups vs multi homed section,
2958  */
2959         /* 
2960          * sgroup,active vs. mhomed,active
2961          * => should NOT be replaced
2962          */
2963         {
2964                 .line   = __location__,
2965                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2966                 .r1     = {
2967                         .owner          = &ctx->a,
2968                         .type           = WREPL_TYPE_SGROUP,
2969                         .state          = WREPL_STATE_ACTIVE,
2970                         .node           = WREPL_NODE_B,
2971                         .is_static      = False,
2972                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2973                         .ips            = addresses_A_1,
2974                         .apply_expected = True
2975                 },
2976                 .r2     = {
2977                         .owner          = &ctx->b,
2978                         .type           = WREPL_TYPE_MHOMED,
2979                         .state          = WREPL_STATE_ACTIVE,
2980                         .node           = WREPL_NODE_B,
2981                         .is_static      = False,
2982                         .num_ips        = ARRAY_SIZE(addresses_A_1),
2983                         .ips            = addresses_A_1,
2984                         .apply_expected = False
2985                 }
2986         },
2987
2988         /* 
2989          * sgroup,active vs. mhomed,tombstone
2990          * => should NOT be replaced
2991          */
2992         {
2993                 .line   = __location__,
2994                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
2995                 .r1     = {
2996                         .owner          = &ctx->a,
2997                         .type           = WREPL_TYPE_SGROUP,
2998                         .state          = WREPL_STATE_ACTIVE,
2999                         .node           = WREPL_NODE_B,
3000                         .is_static      = False,
3001                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3002                         .ips            = addresses_A_1,
3003                         .apply_expected = True
3004                 },
3005                 .r2     = {
3006                         .owner          = &ctx->b,
3007                         .type           = WREPL_TYPE_MHOMED,
3008                         .state          = WREPL_STATE_TOMBSTONE,
3009                         .node           = WREPL_NODE_B,
3010                         .is_static      = False,
3011                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3012                         .ips            = addresses_A_1,
3013                         .apply_expected = False
3014                 }
3015         },
3016
3017         /* 
3018          * sgroup,released vs. mhomed,active
3019          * => should be replaced
3020          */
3021         {
3022                 .line   = __location__,
3023                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3024                 .r1     = {
3025                         .owner          = &ctx->a,
3026                         .type           = WREPL_TYPE_SGROUP,
3027                         .state          = WREPL_STATE_RELEASED,
3028                         .node           = WREPL_NODE_B,
3029                         .is_static      = False,
3030                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3031                         .ips            = addresses_A_1,
3032                         .apply_expected = False
3033                 },
3034                 .r2     = {
3035                         .owner          = &ctx->b,
3036                         .type           = WREPL_TYPE_MHOMED,
3037                         .state          = WREPL_STATE_ACTIVE,
3038                         .node           = WREPL_NODE_B,
3039                         .is_static      = False,
3040                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3041                         .ips            = addresses_B_1,
3042                         .apply_expected = True
3043                 }
3044         },
3045
3046         /* 
3047          * sgroup,released vs. mhomed,tombstone
3048          * => should be replaced
3049          */
3050         {
3051                 .line   = __location__,
3052                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3053                 .r1     = {
3054                         .owner          = &ctx->b,
3055                         .type           = WREPL_TYPE_SGROUP,
3056                         .state          = WREPL_STATE_RELEASED,
3057                         .node           = WREPL_NODE_B,
3058                         .is_static      = False,
3059                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3060                         .ips            = addresses_B_1,
3061                         .apply_expected = False
3062                 },
3063                 .r2     = {
3064                         .owner          = &ctx->a,
3065                         .type           = WREPL_TYPE_MHOMED,
3066                         .state          = WREPL_STATE_TOMBSTONE,
3067                         .node           = WREPL_NODE_B,
3068                         .is_static      = False,
3069                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3070                         .ips            = addresses_A_1,
3071                         .apply_expected = True
3072                 }
3073         },
3074
3075         /* 
3076          * sgroup,tombstone vs. mhomed,active
3077          * => should be replaced
3078          */
3079         {
3080                 .line   = __location__,
3081                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3082                 .r1     = {
3083                         .owner          = &ctx->a,
3084                         .type           = WREPL_TYPE_SGROUP,
3085                         .state          = WREPL_STATE_TOMBSTONE,
3086                         .node           = WREPL_NODE_B,
3087                         .is_static      = False,
3088                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3089                         .ips            = addresses_A_1,
3090                         .apply_expected = True
3091                 },
3092                 .r2     = {
3093                         .owner          = &ctx->b,
3094                         .type           = WREPL_TYPE_MHOMED,
3095                         .state          = WREPL_STATE_ACTIVE,
3096                         .node           = WREPL_NODE_B,
3097                         .is_static      = False,
3098                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3099                         .ips            = addresses_B_1,
3100                         .apply_expected = True
3101                 }
3102         },
3103
3104         /* 
3105          * sgroup,tombstone vs. mhomed,tombstone
3106          * => should be replaced
3107          */
3108         {
3109                 .line   = __location__,
3110                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3111                 .r1     = {
3112                         .owner          = &ctx->b,
3113                         .type           = WREPL_TYPE_SGROUP,
3114                         .state          = WREPL_STATE_TOMBSTONE,
3115                         .node           = WREPL_NODE_B,
3116                         .is_static      = False,
3117                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3118                         .ips            = addresses_B_1,
3119                         .apply_expected = True
3120                 },
3121                 .r2     = {
3122                         .owner          = &ctx->a,
3123                         .type           = WREPL_TYPE_MHOMED,
3124                         .state          = WREPL_STATE_TOMBSTONE,
3125                         .node           = WREPL_NODE_B,
3126                         .is_static      = False,
3127                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3128                         .ips            = addresses_A_1,
3129                         .apply_expected = True
3130                 }
3131         },
3132
3133 /*
3134  * multi homed vs. unique section,
3135  */
3136         /* 
3137          * mhomed,active vs. unique,active
3138          * => should be replaced
3139          */
3140         {
3141                 .line   = __location__,
3142                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3143                 .r1     = {
3144                         .owner          = &ctx->a,
3145                         .type           = WREPL_TYPE_MHOMED,
3146                         .state          = WREPL_STATE_ACTIVE,
3147                         .node           = WREPL_NODE_B,
3148                         .is_static      = False,
3149                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3150                         .ips            = addresses_A_3_4,
3151                         .apply_expected = True
3152                 },
3153                 .r2     = {
3154                         .owner          = &ctx->b,
3155                         .type           = WREPL_TYPE_UNIQUE,
3156                         .state          = WREPL_STATE_ACTIVE,
3157                         .node           = WREPL_NODE_B,
3158                         .is_static      = False,
3159                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3160                         .ips            = addresses_B_1,
3161                         .apply_expected = True
3162                 }
3163         },
3164
3165         /* 
3166          * mhomed,active vs. unique,tombstone
3167          * => should NOT be replaced
3168          */
3169         {
3170                 .line   = __location__,
3171                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3172                 .r1     = {
3173                         .owner          = &ctx->b,
3174                         .type           = WREPL_TYPE_MHOMED,
3175                         .state          = WREPL_STATE_ACTIVE,
3176                         .node           = WREPL_NODE_B,
3177                         .is_static      = False,
3178                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3179                         .ips            = addresses_B_1,
3180                         .apply_expected = True
3181                 },
3182                 .r2     = {
3183                         .owner          = &ctx->a,
3184                         .type           = WREPL_TYPE_UNIQUE,
3185                         .state          = WREPL_STATE_TOMBSTONE,
3186                         .node           = WREPL_NODE_B,
3187                         .is_static      = False,
3188                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3189                         .ips            = addresses_B_1,
3190                         .apply_expected = False
3191                 }
3192         },
3193
3194         /* 
3195          * mhomed,released vs. unique,active
3196          * => should be replaced
3197          */
3198         {
3199                 .line   = __location__,
3200                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3201                 .r1     = {
3202                         .owner          = &ctx->a,
3203                         .type           = WREPL_TYPE_MHOMED,
3204                         .state          = WREPL_STATE_RELEASED,
3205                         .node           = WREPL_NODE_B,
3206                         .is_static      = False,
3207                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3208                         .ips            = addresses_A_1,
3209                         .apply_expected = False
3210                 },
3211                 .r2     = {
3212                         .owner          = &ctx->b,
3213                         .type           = WREPL_TYPE_UNIQUE,
3214                         .state          = WREPL_STATE_ACTIVE,
3215                         .node           = WREPL_NODE_B,
3216                         .is_static      = False,
3217                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3218                         .ips            = addresses_B_1,
3219                         .apply_expected = True
3220                 }
3221         },
3222
3223         /* 
3224          * mhomed,released vs. uinique,tombstone
3225          * => should be replaced
3226          */
3227         {
3228                 .line   = __location__,
3229                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3230                 .r1     = {
3231                         .owner          = &ctx->b,
3232                         .type           = WREPL_TYPE_MHOMED,
3233                         .state          = WREPL_STATE_RELEASED,
3234                         .node           = WREPL_NODE_B,
3235                         .is_static      = False,
3236                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3237                         .ips            = addresses_B_1,
3238                         .apply_expected = False
3239                 },
3240                 .r2     = {
3241                         .owner          = &ctx->a,
3242                         .type           = WREPL_TYPE_UNIQUE,
3243                         .state          = WREPL_STATE_TOMBSTONE,
3244                         .node           = WREPL_NODE_B,
3245                         .is_static      = False,
3246                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3247                         .ips            = addresses_A_1,
3248                         .apply_expected = True
3249                 }
3250         },
3251
3252         /* 
3253          * mhomed,tombstone vs. unique,active
3254          * => should be replaced
3255          */
3256         {
3257                 .line   = __location__,
3258                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3259                 .r1     = {
3260                         .owner          = &ctx->a,
3261                         .type           = WREPL_TYPE_MHOMED,
3262                         .state          = WREPL_STATE_TOMBSTONE,
3263                         .node           = WREPL_NODE_B,
3264                         .is_static      = False,
3265                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3266                         .ips            = addresses_A_1,
3267                         .apply_expected = True
3268                 },
3269                 .r2     = {
3270                         .owner          = &ctx->b,
3271                         .type           = WREPL_TYPE_UNIQUE,
3272                         .state          = WREPL_STATE_ACTIVE,
3273                         .node           = WREPL_NODE_B,
3274                         .is_static      = False,
3275                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3276                         .ips            = addresses_B_1,
3277                         .apply_expected = True
3278                 }
3279         },
3280
3281         /* 
3282          * mhomed,tombstone vs. uinique,tombstone
3283          * => should be replaced
3284          */
3285         {
3286                 .line   = __location__,
3287                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3288                 .r1     = {
3289                         .owner          = &ctx->b,
3290                         .type           = WREPL_TYPE_MHOMED,
3291                         .state          = WREPL_STATE_TOMBSTONE,
3292                         .node           = WREPL_NODE_B,
3293                         .is_static      = False,
3294                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3295                         .ips            = addresses_B_1,
3296                         .apply_expected = True
3297                 },
3298                 .r2     = {
3299                         .owner          = &ctx->a,
3300                         .type           = WREPL_TYPE_UNIQUE,
3301                         .state          = WREPL_STATE_TOMBSTONE,
3302                         .node           = WREPL_NODE_B,
3303                         .is_static      = False,
3304                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3305                         .ips            = addresses_A_1,
3306                         .apply_expected = True
3307                 }
3308         },
3309
3310 /*
3311  * multi homed vs. normal group section,
3312  */
3313         /* 
3314          * mhomed,active vs. group,active
3315          * => should be replaced
3316          */
3317         {
3318                 .line   = __location__,
3319                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3320                 .r1     = {
3321                         .owner          = &ctx->a,
3322                         .type           = WREPL_TYPE_MHOMED,
3323                         .state          = WREPL_STATE_ACTIVE,
3324                         .node           = WREPL_NODE_B,
3325                         .is_static      = False,
3326                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3327                         .ips            = addresses_A_1,
3328                         .apply_expected = True
3329                 },
3330                 .r2     = {
3331                         .owner          = &ctx->b,
3332                         .type           = WREPL_TYPE_GROUP,
3333                         .state          = WREPL_STATE_ACTIVE,
3334                         .node           = WREPL_NODE_B,
3335                         .is_static      = False,
3336                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3337                         .ips            = addresses_B_1,
3338                         .apply_expected = True
3339                 }
3340         },
3341
3342         /* 
3343          * mhomed,active vs. group,tombstone
3344          * => should NOT be replaced
3345          */
3346         {
3347                 .line   = __location__,
3348                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3349                 .r1     = {
3350                         .owner          = &ctx->b,
3351                         .type           = WREPL_TYPE_MHOMED,
3352                         .state          = WREPL_STATE_ACTIVE,
3353                         .node           = WREPL_NODE_B,
3354                         .is_static      = False,
3355                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3356                         .ips            = addresses_B_1,
3357                         .apply_expected = True
3358                 },
3359                 .r2     = {
3360                         .owner          = &ctx->a,
3361                         .type           = WREPL_TYPE_GROUP,
3362                         .state          = WREPL_STATE_TOMBSTONE,
3363                         .node           = WREPL_NODE_B,
3364                         .is_static      = False,
3365                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3366                         .ips            = addresses_B_1,
3367                         .apply_expected = False
3368                 }
3369         },
3370
3371         /* 
3372          * mhomed,released vs. group,active
3373          * => should be replaced
3374          */
3375         {
3376                 .line   = __location__,
3377                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3378                 .r1     = {
3379                         .owner          = &ctx->b,
3380                         .type           = WREPL_TYPE_MHOMED,
3381                         .state          = WREPL_STATE_RELEASED,
3382                         .node           = WREPL_NODE_B,
3383                         .is_static      = False,
3384                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3385                         .ips            = addresses_B_1,
3386                         .apply_expected = False
3387                 },
3388                 .r2     = {
3389                         .owner          = &ctx->a,
3390                         .type           = WREPL_TYPE_GROUP,
3391                         .state          = WREPL_STATE_ACTIVE,
3392                         .node           = WREPL_NODE_B,
3393                         .is_static      = False,
3394                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3395                         .ips            = addresses_A_1,
3396                         .apply_expected = True
3397                 }
3398         },
3399
3400         /* 
3401          * mhomed,released vs. group,tombstone
3402          * => should be replaced
3403          */
3404         {
3405                 .line   = __location__,
3406                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3407                 .r1     = {
3408                         .owner          = &ctx->a,
3409                         .type           = WREPL_TYPE_MHOMED,
3410                         .state          = WREPL_STATE_RELEASED,
3411                         .node           = WREPL_NODE_B,
3412                         .is_static      = False,
3413                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3414                         .ips            = addresses_A_1,
3415                         .apply_expected = False
3416                 },
3417                 .r2     = {
3418                         .owner          = &ctx->b,
3419                         .type           = WREPL_TYPE_GROUP,
3420                         .state          = WREPL_STATE_TOMBSTONE,
3421                         .node           = WREPL_NODE_B,
3422                         .is_static      = False,
3423                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3424                         .ips            = addresses_B_1,
3425                         .apply_expected = True
3426                 }
3427         },
3428
3429         /* 
3430          * mhomed,tombstone vs. group,active
3431          * => should be replaced
3432          */
3433         {
3434                 .line   = __location__,
3435                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3436                 .r1     = {
3437                         .owner          = &ctx->b,
3438                         .type           = WREPL_TYPE_MHOMED,
3439                         .state          = WREPL_STATE_TOMBSTONE,
3440                         .node           = WREPL_NODE_B,
3441                         .is_static      = False,
3442                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3443                         .ips            = addresses_B_1,
3444                         .apply_expected = True
3445                 },
3446                 .r2     = {
3447                         .owner          = &ctx->a,
3448                         .type           = WREPL_TYPE_GROUP,
3449                         .state          = WREPL_STATE_ACTIVE,
3450                         .node           = WREPL_NODE_B,
3451                         .is_static      = False,
3452                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3453                         .ips            = addresses_A_1,
3454                         .apply_expected = True
3455                 }
3456         },
3457
3458         /* 
3459          * mhomed,tombstone vs. group,tombstone
3460          * => should be replaced
3461          */
3462         {
3463                 .line   = __location__,
3464                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3465                 .r1     = {
3466                         .owner          = &ctx->a,
3467                         .type           = WREPL_TYPE_MHOMED,
3468                         .state          = WREPL_STATE_TOMBSTONE,
3469                         .node           = WREPL_NODE_B,
3470                         .is_static      = False,
3471                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3472                         .ips            = addresses_A_1,
3473                         .apply_expected = True
3474                 },
3475                 .r2     = {
3476                         .owner          = &ctx->b,
3477                         .type           = WREPL_TYPE_GROUP,
3478                         .state          = WREPL_STATE_TOMBSTONE,
3479                         .node           = WREPL_NODE_B,
3480                         .is_static      = False,
3481                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3482                         .ips            = addresses_B_1,
3483                         .apply_expected = True
3484                 }
3485         },
3486
3487 /*
3488  * multi homed vs. special group section,
3489  */
3490         /* 
3491          * mhomed,active vs. sgroup,active
3492          * => should NOT be replaced
3493          */
3494         {
3495                 .line   = __location__,
3496                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3497                 .r1     = {
3498                         .owner          = &ctx->a,
3499                         .type           = WREPL_TYPE_MHOMED,
3500                         .state          = WREPL_STATE_ACTIVE,
3501                         .node           = WREPL_NODE_B,
3502                         .is_static      = False,
3503                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3504                         .ips            = addresses_A_1,
3505                         .apply_expected = True
3506                 },
3507                 .r2     = {
3508                         .owner          = &ctx->b,
3509                         .type           = WREPL_TYPE_SGROUP,
3510                         .state          = WREPL_STATE_ACTIVE,
3511                         .node           = WREPL_NODE_B,
3512                         .is_static      = False,
3513                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3514                         .ips            = addresses_A_1,
3515                         .apply_expected = False
3516                 }
3517         },
3518
3519         /* 
3520          * mhomed,active vs. sgroup,tombstone
3521          * => should NOT be replaced
3522          */
3523         {
3524                 .line   = __location__,
3525                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3526                 .r1     = {
3527                         .owner          = &ctx->a,
3528                         .type           = WREPL_TYPE_MHOMED,
3529                         .state          = WREPL_STATE_ACTIVE,
3530                         .node           = WREPL_NODE_B,
3531                         .is_static      = False,
3532                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3533                         .ips            = addresses_A_1,
3534                         .apply_expected = True
3535                 },
3536                 .r2     = {
3537                         .owner          = &ctx->b,
3538                         .type           = WREPL_TYPE_SGROUP,
3539                         .state          = WREPL_STATE_TOMBSTONE,
3540                         .node           = WREPL_NODE_B,
3541                         .is_static      = False,
3542                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3543                         .ips            = addresses_A_1,
3544                         .apply_expected = False
3545                 }
3546         },
3547
3548         /* 
3549          * mhomed,released vs. sgroup,active
3550          * => should be replaced
3551          */
3552         {
3553                 .line   = __location__,
3554                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3555                 .r1     = {
3556                         .owner          = &ctx->a,
3557                         .type           = WREPL_TYPE_MHOMED,
3558                         .state          = WREPL_STATE_RELEASED,
3559                         .node           = WREPL_NODE_B,
3560                         .is_static      = False,
3561                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3562                         .ips            = addresses_A_1,
3563                         .apply_expected = False
3564                 },
3565                 .r2     = {
3566                         .owner          = &ctx->b,
3567                         .type           = WREPL_TYPE_SGROUP,
3568                         .state          = WREPL_STATE_ACTIVE,
3569                         .node           = WREPL_NODE_B,
3570                         .is_static      = False,
3571                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3572                         .ips            = addresses_B_1,
3573                         .apply_expected = True
3574                 }
3575         },
3576
3577         /* 
3578          * mhomed,released vs. sgroup,tombstone
3579          * => should be replaced
3580          */
3581         {
3582                 .line   = __location__,
3583                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3584                 .r1     = {
3585                         .owner          = &ctx->b,
3586                         .type           = WREPL_TYPE_MHOMED,
3587                         .state          = WREPL_STATE_RELEASED,
3588                         .node           = WREPL_NODE_B,
3589                         .is_static      = False,
3590                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3591                         .ips            = addresses_B_1,
3592                         .apply_expected = False
3593                 },
3594                 .r2     = {
3595                         .owner          = &ctx->a,
3596                         .type           = WREPL_TYPE_SGROUP,
3597                         .state          = WREPL_STATE_TOMBSTONE,
3598                         .node           = WREPL_NODE_B,
3599                         .is_static      = False,
3600                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3601                         .ips            = addresses_A_1,
3602                         .apply_expected = True
3603                 }
3604         },
3605
3606         /* 
3607          * mhomed,tombstone vs. sgroup,active
3608          * => should be replaced
3609          */
3610         {
3611                 .line   = __location__,
3612                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3613                 .r1     = {
3614                         .owner          = &ctx->a,
3615                         .type           = WREPL_TYPE_MHOMED,
3616                         .state          = WREPL_STATE_TOMBSTONE,
3617                         .node           = WREPL_NODE_B,
3618                         .is_static      = False,
3619                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3620                         .ips            = addresses_A_1,
3621                         .apply_expected = True
3622                 },
3623                 .r2     = {
3624                         .owner          = &ctx->b,
3625                         .type           = WREPL_TYPE_SGROUP,
3626                         .state          = WREPL_STATE_ACTIVE,
3627                         .node           = WREPL_NODE_B,
3628                         .is_static      = False,
3629                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3630                         .ips            = addresses_B_1,
3631                         .apply_expected = True
3632                 }
3633         },
3634
3635         /* 
3636          * mhomed,tombstone vs. sgroup,tombstone
3637          * => should be replaced
3638          */
3639         {
3640                 .line   = __location__,
3641                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3642                 .r1     = {
3643                         .owner          = &ctx->b,
3644                         .type           = WREPL_TYPE_MHOMED,
3645                         .state          = WREPL_STATE_TOMBSTONE,
3646                         .node           = WREPL_NODE_B,
3647                         .is_static      = False,
3648                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3649                         .ips            = addresses_B_1,
3650                         .apply_expected = True
3651                 },
3652                 .r2     = {
3653                         .owner          = &ctx->a,
3654                         .type           = WREPL_TYPE_SGROUP,
3655                         .state          = WREPL_STATE_TOMBSTONE,
3656                         .node           = WREPL_NODE_B,
3657                         .is_static      = False,
3658                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3659                         .ips            = addresses_A_1,
3660                         .apply_expected = True
3661                 }
3662         },
3663
3664 /*
3665  * multi homed vs. mlti homed section,
3666  */
3667         /* 
3668          * mhomed,active vs. mhomed,active
3669          * => should be replaced
3670          */
3671         {
3672                 .line   = __location__,
3673                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3674                 .r1     = {
3675                         .owner          = &ctx->a,
3676                         .type           = WREPL_TYPE_MHOMED,
3677                         .state          = WREPL_STATE_ACTIVE,
3678                         .node           = WREPL_NODE_B,
3679                         .is_static      = False,
3680                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3681                         .ips            = addresses_A_3_4,
3682                         .apply_expected = True
3683                 },
3684                 .r2     = {
3685                         .owner          = &ctx->b,
3686                         .type           = WREPL_TYPE_MHOMED,
3687                         .state          = WREPL_STATE_ACTIVE,
3688                         .node           = WREPL_NODE_B,
3689                         .is_static      = False,
3690                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3691                         .ips            = addresses_B_3_4,
3692                         .apply_expected = True
3693                 }
3694         },
3695
3696         /* 
3697          * mhomed,active vs. mhomed,tombstone
3698          * => should NOT be replaced
3699          */
3700         {
3701                 .line   = __location__,
3702                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3703                 .r1     = {
3704                         .owner          = &ctx->b,
3705                         .type           = WREPL_TYPE_MHOMED,
3706                         .state          = WREPL_STATE_ACTIVE,
3707                         .node           = WREPL_NODE_B,
3708                         .is_static      = False,
3709                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3710                         .ips            = addresses_B_3_4,
3711                         .apply_expected = True
3712                 },
3713                 .r2     = {
3714                         .owner          = &ctx->a,
3715                         .type           = WREPL_TYPE_MHOMED,
3716                         .state          = WREPL_STATE_TOMBSTONE,
3717                         .node           = WREPL_NODE_B,
3718                         .is_static      = False,
3719                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3720                         .ips            = addresses_B_3_4,
3721                         .apply_expected = False
3722                 }
3723         },
3724
3725         /* 
3726          * mhomed,released vs. mhomed,active
3727          * => should be replaced
3728          */
3729         {
3730                 .line   = __location__,
3731                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3732                 .r1     = {
3733                         .owner          = &ctx->b,
3734                         .type           = WREPL_TYPE_MHOMED,
3735                         .state          = WREPL_STATE_RELEASED,
3736                         .node           = WREPL_NODE_B,
3737                         .is_static      = False,
3738                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3739                         .ips            = addresses_B_3_4,
3740                         .apply_expected = False
3741                 },
3742                 .r2     = {
3743                         .owner          = &ctx->a,
3744                         .type           = WREPL_TYPE_MHOMED,
3745                         .state          = WREPL_STATE_ACTIVE,
3746                         .node           = WREPL_NODE_B,
3747                         .is_static      = False,
3748                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3749                         .ips            = addresses_A_3_4,
3750                         .apply_expected = True
3751                 }
3752         },
3753
3754         /* 
3755          * mhomed,released vs. mhomed,tombstone
3756          * => should be replaced
3757          */
3758         {
3759                 .line   = __location__,
3760                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3761                 .r1     = {
3762                         .owner          = &ctx->a,
3763                         .type           = WREPL_TYPE_MHOMED,
3764                         .state          = WREPL_STATE_RELEASED,
3765                         .node           = WREPL_NODE_B,
3766                         .is_static      = False,
3767                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3768                         .ips            = addresses_A_3_4,
3769                         .apply_expected = False
3770                 },
3771                 .r2     = {
3772                         .owner          = &ctx->b,
3773                         .type           = WREPL_TYPE_MHOMED,
3774                         .state          = WREPL_STATE_TOMBSTONE,
3775                         .node           = WREPL_NODE_B,
3776                         .is_static      = False,
3777                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3778                         .ips            = addresses_B_3_4,
3779                         .apply_expected = True
3780                 }
3781         },
3782
3783         /* 
3784          * mhomed,tombstone vs. mhomed,active
3785          * => should be replaced
3786          */
3787         {
3788                 .line   = __location__,
3789                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3790                 .r1     = {
3791                         .owner          = &ctx->b,
3792                         .type           = WREPL_TYPE_MHOMED,
3793                         .state          = WREPL_STATE_TOMBSTONE,
3794                         .node           = WREPL_NODE_B,
3795                         .is_static      = False,
3796                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3797                         .ips            = addresses_B_3_4,
3798                         .apply_expected = True
3799                 },
3800                 .r2     = {
3801                         .owner          = &ctx->a,
3802                         .type           = WREPL_TYPE_MHOMED,
3803                         .state          = WREPL_STATE_ACTIVE,
3804                         .node           = WREPL_NODE_B,
3805                         .is_static      = False,
3806                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3807                         .ips            = addresses_A_3_4,
3808                         .apply_expected = True
3809                 }
3810         },
3811
3812         /* 
3813          * mhomed,tombstone vs. mhomed,tombstone
3814          * => should be replaced
3815          */
3816         {
3817                 .line   = __location__,
3818                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3819                 .r1     = {
3820                         .owner          = &ctx->a,
3821                         .type           = WREPL_TYPE_MHOMED,
3822                         .state          = WREPL_STATE_TOMBSTONE,
3823                         .node           = WREPL_NODE_B,
3824                         .is_static      = False,
3825                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3826                         .ips            = addresses_A_3_4,
3827                         .apply_expected = True
3828                 },
3829                 .r2     = {
3830                         .owner          = &ctx->b,
3831                         .type           = WREPL_TYPE_MHOMED,
3832                         .state          = WREPL_STATE_TOMBSTONE,
3833                         .node           = WREPL_NODE_B,
3834                         .is_static      = False,
3835                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3836                         .ips            = addresses_B_3_4,
3837                         .apply_expected = True
3838                 }
3839         },
3840         {
3841                 .line   = __location__,
3842                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3843                 .cleanup= True,
3844                 .r1     = {
3845                         .owner          = &ctx->b,
3846                         .type           = WREPL_TYPE_UNIQUE,
3847                         .state          = WREPL_STATE_TOMBSTONE,
3848                         .node           = WREPL_NODE_B,
3849                         .is_static      = False,
3850                         .num_ips        = ARRAY_SIZE(addresses_B_1),
3851                         .ips            = addresses_B_1,
3852                         .apply_expected = True,
3853                 },
3854                 .r2     = {
3855                         .owner          = &ctx->a,
3856                         .type           = WREPL_TYPE_UNIQUE,
3857                         .state          = WREPL_STATE_TOMBSTONE,
3858                         .node           = WREPL_NODE_B,
3859                         .is_static      = False,
3860                         .num_ips        = ARRAY_SIZE(addresses_A_1),
3861                         .ips            = addresses_A_1,
3862                         .apply_expected = True,
3863                 }
3864         },
3865 /*
3866  * special group vs special group section,
3867  */
3868         /* 
3869          * sgroup,active vs. sgroup,active different addresses
3870          * => should be merged
3871          */
3872         {
3873                 .line   = __location__,
3874                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3875                 .comment= "A:A_3_4 vs. B:B_3_4 => C:A_3_4_B_3_4",
3876                 .extra  = True,
3877                 .r1     = {
3878                         .owner          = &ctx->a,
3879                         .type           = WREPL_TYPE_SGROUP,
3880                         .state          = WREPL_STATE_ACTIVE,
3881                         .node           = WREPL_NODE_B,
3882                         .is_static      = False,
3883                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3884                         .ips            = addresses_A_3_4,
3885                         .apply_expected = True,
3886                 },
3887                 .r2     = {
3888                         .owner          = &ctx->b,
3889                         .type           = WREPL_TYPE_SGROUP,
3890                         .state          = WREPL_STATE_ACTIVE,
3891                         .node           = WREPL_NODE_B,
3892                         .is_static      = False,
3893                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3894                         .ips            = addresses_B_3_4,
3895                         .sgroup_merge   = True,
3896                         .sgroup_cleanup = True,
3897                 }
3898         },
3899         /* 
3900          * sgroup,active vs. sgroup,active same addresses
3901          * => should be NOT replaced
3902          */
3903         {
3904                 .line   = __location__,
3905                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3906                 .comment= "A:A_3_4 vs. B:A_3_4",
3907                 .extra  = True,
3908                 .r1     = {
3909                         .owner          = &ctx->a,
3910                         .type           = WREPL_TYPE_SGROUP,
3911                         .state          = WREPL_STATE_ACTIVE,
3912                         .node           = WREPL_NODE_B,
3913                         .is_static      = False,
3914                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3915                         .ips            = addresses_A_3_4,
3916                         .apply_expected = True
3917                 },
3918                 .r2     = {
3919                         .owner          = &ctx->b,
3920                         .type           = WREPL_TYPE_SGROUP,
3921                         .state          = WREPL_STATE_ACTIVE,
3922                         .node           = WREPL_NODE_B,
3923                         .is_static      = False,
3924                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3925                         .ips            = addresses_A_3_4,
3926                         .apply_expected = False,
3927                         .sgroup_cleanup = True
3928                 }
3929         },
3930         /* 
3931          * sgroup,active vs. sgroup,active different addresses, but owner changed
3932          * => should be replaced
3933          */
3934         {
3935                 .line   = __location__,
3936                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3937                 .comment= "A:B_3_4 vs. B:A_3_4",
3938                 .extra  = True,
3939                 .r1     = {
3940                         .owner          = &ctx->a,
3941                         .type           = WREPL_TYPE_SGROUP,
3942                         .state          = WREPL_STATE_ACTIVE,
3943                         .node           = WREPL_NODE_B,
3944                         .is_static      = False,
3945                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
3946                         .ips            = addresses_B_3_4,
3947                         .apply_expected = True,
3948                 },
3949                 .r2     = {
3950                         .owner          = &ctx->b,
3951                         .type           = WREPL_TYPE_SGROUP,
3952                         .state          = WREPL_STATE_ACTIVE,
3953                         .node           = WREPL_NODE_B,
3954                         .is_static      = False,
3955                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3956                         .ips            = addresses_A_3_4,
3957                         .apply_expected = True,
3958                         .sgroup_cleanup = True
3959                 }
3960         },
3961         /* 
3962          * sgroup,active vs. sgroup,active different addresses, but owner changed
3963          * => should be replaced
3964          */
3965         {
3966                 .line   = __location__,
3967                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3968                 .comment= "A:A_3_4 vs. B:A_3_4_OWNER_B",
3969                 .extra  = True,
3970                 .r1     = {
3971                         .owner          = &ctx->a,
3972                         .type           = WREPL_TYPE_SGROUP,
3973                         .state          = WREPL_STATE_ACTIVE,
3974                         .node           = WREPL_NODE_B,
3975                         .is_static      = False,
3976                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
3977                         .ips            = addresses_A_3_4,
3978                         .apply_expected = True,
3979                 },
3980                 .r2     = {
3981                         .owner          = &ctx->b,
3982                         .type           = WREPL_TYPE_SGROUP,
3983                         .state          = WREPL_STATE_ACTIVE,
3984                         .node           = WREPL_NODE_B,
3985                         .is_static      = False,
3986                         .num_ips        = ARRAY_SIZE(addresses_A_3_4_OWNER_B),
3987                         .ips            = addresses_A_3_4_OWNER_B,
3988                         .apply_expected = True,
3989                         .sgroup_cleanup = True
3990                 }
3991         },
3992         /* 
3993          * sgroup,active vs. sgroup,active different addresses, but owner changed
3994          * => should be replaced
3995          */
3996         {
3997                 .line   = __location__,
3998                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
3999                 .comment= "A:A_3_4_OWNER_B vs. B:A_3_4",
4000                 .extra  = True,
4001                 .r1     = {
4002                         .owner          = &ctx->a,
4003                         .type           = WREPL_TYPE_SGROUP,
4004                         .state          = WREPL_STATE_ACTIVE,
4005                         .node           = WREPL_NODE_B,
4006                         .is_static      = False,
4007                         .num_ips        = ARRAY_SIZE(addresses_A_3_4_OWNER_B),
4008                         .ips            = addresses_A_3_4_OWNER_B,
4009                         .apply_expected = True,
4010                 },
4011                 .r2     = {
4012                         .owner          = &ctx->b,
4013                         .type           = WREPL_TYPE_SGROUP,
4014                         .state          = WREPL_STATE_ACTIVE,
4015                         .node           = WREPL_NODE_B,
4016                         .is_static      = False,
4017                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
4018                         .ips            = addresses_A_3_4,
4019                         .apply_expected = True,
4020                         .sgroup_cleanup = True
4021                 }
4022         },
4023         /* 
4024          * sgroup,active vs. sgroup,active different addresses, special case...
4025          * => should be merged
4026          */
4027         {
4028                 .line   = __location__,
4029                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4030                 .comment= "A:B_3_4_X_3_4 vs. B:A_3_4 => B:X_3_4",
4031                 .extra  = True,
4032                 .r1     = {
4033                         .owner          = &ctx->a,
4034                         .type           = WREPL_TYPE_SGROUP,
4035                         .state          = WREPL_STATE_ACTIVE,
4036                         .node           = WREPL_NODE_B,
4037                         .is_static      = False,
4038                         .num_ips        = ARRAY_SIZE(addresses_B_3_4_X_3_4),
4039                         .ips            = addresses_B_3_4_X_3_4,
4040                         .apply_expected = True,
4041                 },
4042                 .r2     = {
4043                         .owner          = &ctx->b,
4044                         .type           = WREPL_TYPE_SGROUP,
4045                         .state          = WREPL_STATE_ACTIVE,
4046                         .node           = WREPL_NODE_B,
4047                         .is_static      = False,
4048                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
4049                         .ips            = addresses_A_3_4,
4050                         .sgroup_merge   = True,
4051                         .merge_owner    = &ctx->b,
4052                         .sgroup_cleanup = False
4053                 }
4054         },
4055         {
4056                 .line   = __location__,
4057                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4058                 .cleanup= True,
4059                 .r1     = {
4060                         .owner          = &ctx->b,
4061                         .type           = WREPL_TYPE_SGROUP,
4062                         .state          = WREPL_STATE_ACTIVE,
4063                         .node           = WREPL_NODE_B,
4064                         .is_static      = False,
4065                         .num_ips        = ARRAY_SIZE(addresses_A_3_4_X_3_4_OWNER_B),
4066                         .ips            = addresses_A_3_4_X_3_4_OWNER_B,
4067                         .apply_expected = True,
4068                 },
4069                 .r2     = {
4070                         .owner          = &ctx->b,
4071                         .type           = WREPL_TYPE_SGROUP,
4072                         .state          = WREPL_STATE_ACTIVE,
4073                         .node           = WREPL_NODE_B,
4074                         .is_static      = False,
4075                         .num_ips        = 0,
4076                         .ips            = NULL,
4077                         .apply_expected = False,
4078                 }
4079         },
4080         /* 
4081          * sgroup,active vs. sgroup,active subset addresses, special case...
4082          * => should NOT be replaced
4083          */
4084         {
4085                 .line   = __location__,
4086                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4087                 .comment= "A:A_3_4_X_3_4 vs. B:A_3_4",
4088                 .extra  = True,
4089                 .r1     = {
4090                         .owner          = &ctx->a,
4091                         .type           = WREPL_TYPE_SGROUP,
4092                         .state          = WREPL_STATE_ACTIVE,
4093                         .node           = WREPL_NODE_B,
4094                         .is_static      = False,
4095                         .num_ips        = ARRAY_SIZE(addresses_A_3_4_X_3_4),
4096                         .ips            = addresses_A_3_4_X_3_4,
4097                         .apply_expected = True,
4098                 },
4099                 .r2     = {
4100                         .owner          = &ctx->b,
4101                         .type           = WREPL_TYPE_SGROUP,
4102                         .state          = WREPL_STATE_ACTIVE,
4103                         .node           = WREPL_NODE_B,
4104                         .is_static      = False,
4105                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
4106                         .ips            = addresses_A_3_4,
4107                         .apply_expected = False,
4108                 }
4109         },
4110         {
4111                 .line   = __location__,
4112                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4113                 .cleanup= True,
4114                 .r1     = {
4115                         .owner          = &ctx->a,
4116                         .type           = WREPL_TYPE_SGROUP,
4117                         .state          = WREPL_STATE_ACTIVE,
4118                         .node           = WREPL_NODE_B,
4119                         .is_static      = False,
4120                         .num_ips        = 0,
4121                         .ips            = NULL,
4122                         .apply_expected = False,
4123                 },
4124                 .r2     = {
4125                         .owner          = &ctx->x,
4126                         .type           = WREPL_TYPE_SGROUP,
4127                         .state          = WREPL_STATE_ACTIVE,
4128                         .node           = WREPL_NODE_B,
4129                         .is_static      = False,
4130                         .num_ips        = 0,
4131                         .ips            = NULL,
4132                         .apply_expected = False,
4133                 }
4134         },
4135         /* 
4136          * sgroup,active vs. sgroup,active different addresses, special case...
4137          * => should be merged
4138          */
4139         {
4140                 .line   = __location__,
4141                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4142                 .comment= "A:A_3_4_X_3_4 vs. B:A_3_4_OWNER_B => B:A_3_4_OWNER_B_X_3_4",
4143                 .extra  = True,
4144                 .r1     = {
4145                         .owner          = &ctx->a,
4146                         .type           = WREPL_TYPE_SGROUP,
4147                         .state          = WREPL_STATE_ACTIVE,
4148                         .node           = WREPL_NODE_B,
4149                         .is_static      = False,
4150                         .num_ips        = ARRAY_SIZE(addresses_A_3_4_X_3_4),
4151                         .ips            = addresses_A_3_4_X_3_4,
4152                         .apply_expected = True,
4153                 },
4154                 .r2     = {
4155                         .owner          = &ctx->b,
4156                         .type           = WREPL_TYPE_SGROUP,
4157                         .state          = WREPL_STATE_ACTIVE,
4158                         .node           = WREPL_NODE_B,
4159                         .is_static      = False,
4160                         .num_ips        = ARRAY_SIZE(addresses_A_3_4_OWNER_B),
4161                         .ips            = addresses_A_3_4_OWNER_B,
4162                         .sgroup_merge   = True,
4163                         .merge_owner    = &ctx->b,
4164                 }
4165         },
4166         {
4167                 .line   = __location__,
4168                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4169                 .cleanup= True,
4170                 .r1     = {
4171                         .owner          = &ctx->b,
4172                         .type           = WREPL_TYPE_SGROUP,
4173                         .state          = WREPL_STATE_ACTIVE,
4174                         .node           = WREPL_NODE_B,
4175                         .is_static      = False,
4176                         .num_ips        = 0,
4177                         .ips            = NULL,
4178                         .apply_expected = False,
4179                 },
4180                 .r2     = {
4181                         .owner          = &ctx->x,
4182                         .type           = WREPL_TYPE_SGROUP,
4183                         .state          = WREPL_STATE_ACTIVE,
4184                         .node           = WREPL_NODE_B,
4185                         .is_static      = False,
4186                         .num_ips        = 0,
4187                         .ips            = NULL,
4188                         .apply_expected = False,
4189                 }
4190         },
4191         /* 
4192          * sgroup,active vs. sgroup,active partly different addresses, special case...
4193          * => should be merged
4194          */
4195         {
4196                 .line   = __location__,
4197                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4198                 .comment= "A:B_3_4_X_3_4 vs. B:B_3_4_X_1_2 => C:B_3_4_X_1_2_3_4",
4199                 .extra  = True,
4200                 .r1     = {
4201                         .owner          = &ctx->a,
4202                         .type           = WREPL_TYPE_SGROUP,
4203                         .state          = WREPL_STATE_ACTIVE,
4204                         .node           = WREPL_NODE_B,
4205                         .is_static      = False,
4206                         .num_ips        = ARRAY_SIZE(addresses_B_3_4_X_3_4),
4207                         .ips            = addresses_B_3_4_X_3_4,
4208                         .apply_expected = True,
4209                 },
4210                 .r2     = {
4211                         .owner          = &ctx->b,
4212                         .type           = WREPL_TYPE_SGROUP,
4213                         .state          = WREPL_STATE_ACTIVE,
4214                         .node           = WREPL_NODE_B,
4215                         .is_static      = False,
4216                         .num_ips        = ARRAY_SIZE(addresses_B_3_4_X_1_2),
4217                         .ips            = addresses_B_3_4_X_1_2,
4218                         .sgroup_merge   = True,
4219                         .sgroup_cleanup = False
4220                 }
4221         },
4222         {
4223                 .line   = __location__,
4224                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4225                 .cleanup= True,
4226                 .r1     = {
4227                         .owner          = &ctx->b,
4228                         .type           = WREPL_TYPE_SGROUP,
4229                         .state          = WREPL_STATE_ACTIVE,
4230                         .node           = WREPL_NODE_B,
4231                         .is_static      = False,
4232                         .num_ips        = 0,
4233                         .ips            = NULL,
4234                         .apply_expected = False,
4235                 },
4236                 .r2     = {
4237                         .owner          = &ctx->x,
4238                         .type           = WREPL_TYPE_SGROUP,
4239                         .state          = WREPL_STATE_ACTIVE,
4240                         .node           = WREPL_NODE_B,
4241                         .is_static      = False,
4242                         .num_ips        = 0,
4243                         .ips            = NULL,
4244                         .apply_expected = False,
4245                 }
4246         },
4247         /* 
4248          * sgroup,active vs. sgroup,active different addresses, special case...
4249          * => should be merged
4250          */
4251         {
4252                 .line   = __location__,
4253                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4254                 .comment= "A:B_3_4_X_3_4 vs. B:NULL => B:X_3_4",
4255                 .extra  = True,
4256                 .r1     = {
4257                         .owner          = &ctx->a,
4258                         .type           = WREPL_TYPE_SGROUP,
4259                         .state          = WREPL_STATE_ACTIVE,
4260                         .node           = WREPL_NODE_B,
4261                         .is_static      = False,
4262                         .num_ips        = ARRAY_SIZE(addresses_B_3_4_X_3_4),
4263                         .ips            = addresses_B_3_4_X_3_4,
4264                         .apply_expected = True,
4265                 },
4266                 .r2     = {
4267                         .owner          = &ctx->b,
4268                         .type           = WREPL_TYPE_SGROUP,
4269                         .state          = WREPL_STATE_ACTIVE,
4270                         .node           = WREPL_NODE_B,
4271                         .is_static      = False,
4272                         .num_ips        = 0,
4273                         .ips            = NULL,
4274                         .sgroup_merge   = True,
4275                         .merge_owner    = &ctx->b,
4276                         .sgroup_cleanup = True
4277                 }
4278         },
4279         {
4280                 .line   = __location__,
4281                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4282                 .cleanup= True,
4283                 .r1     = {
4284                         .owner          = &ctx->x,
4285                         .type           = WREPL_TYPE_SGROUP,
4286                         .state          = WREPL_STATE_ACTIVE,
4287                         .node           = WREPL_NODE_B,
4288                         .is_static      = False,
4289                         .num_ips        = 0,
4290                         .ips            = NULL,
4291                         .apply_expected = False,
4292                 },
4293                 .r2     = {
4294                         .owner          = &ctx->x,
4295                         .type           = WREPL_TYPE_UNIQUE,
4296                         .state          = WREPL_STATE_TOMBSTONE,
4297                         .node           = WREPL_NODE_B,
4298                         .is_static      = False,
4299                         .num_ips        = ARRAY_SIZE(addresses_A_1),
4300                         .ips            = addresses_A_1,
4301                         .apply_expected = True,
4302                 }
4303         },
4304         /* 
4305          * This should be the last record in this array,
4306          * we need to make sure the we leave a tombstoned unique entry
4307          * owned by OWNER_A
4308          */
4309         {
4310                 .line   = __location__,
4311                 .name   = _NBT_NAME("_DIFF_OWNER", 0x00, NULL),
4312                 .cleanup= True,
4313                 .r1     = {
4314                         .owner          = &ctx->a,
4315                         .type           = WREPL_TYPE_UNIQUE,
4316                         .state          = WREPL_STATE_TOMBSTONE,
4317                         .node           = WREPL_NODE_B,
4318                         .is_static      = False,
4319                         .num_ips        = ARRAY_SIZE(addresses_A_1),
4320                         .ips            = addresses_A_1,
4321                         .apply_expected = True
4322                 },
4323                 .r2     = {
4324                         .owner          = &ctx->a,
4325                         .type           = WREPL_TYPE_UNIQUE,
4326                         .state          = WREPL_STATE_TOMBSTONE,
4327                         .node           = WREPL_NODE_B,
4328                         .is_static      = False,
4329                         .num_ips        = ARRAY_SIZE(addresses_A_1),
4330                         .ips            = addresses_A_1,
4331                         .apply_expected = True
4332                 }
4333         }}; /* do not add entries here, this should be the last record! */
4334
4335         if (!ctx) return False;
4336
4337         wins_name_r1    = &wins_name1;
4338         wins_name_r2    = &wins_name2;
4339
4340         printf("Test Replica Conflicts with different owners\n");
4341
4342         for(i=0; ret && i < ARRAY_SIZE(records); i++) {
4343         
4344                 if (!records[i].extra && !records[i].cleanup) {
4345                         /* we should test the worst cases */
4346                         if (records[i].r2.apply_expected && records[i].r1.ips==records[i].r2.ips) {
4347                                 printf("(%s) Programmer error, invalid record[%u]: %s\n",
4348                                         __location__, i, records[i].line);
4349                                 return False;
4350                         } else if (!records[i].r2.apply_expected && records[i].r1.ips!=records[i].r2.ips) {
4351                                 printf("(%s) Programmer error, invalid record[%u]: %s\n",
4352                                         __location__, i, records[i].line);
4353                                 return False;
4354                         }
4355                 }
4356
4357                 if (!records[i].cleanup) {
4358                         const char *expected;
4359                         const char *ips;
4360
4361                         if (records[i].r2.sgroup_merge) {
4362                                 expected = "SGROUP_MERGE";
4363                         } else if (records[i].r2.apply_expected) {
4364                                 expected = "REPLACE";
4365                         } else {
4366                                 expected = "NOT REPLACE";
4367                         }
4368
4369                         if (!records[i].r1.ips && !records[i].r2.ips) {
4370                                 ips = "with no ip(s)";
4371                         } else if (records[i].r1.ips==records[i].r2.ips) {
4372                                 ips = "with same ip(s)";
4373                         } else {
4374                                 ips = "with different ip(s)";
4375                         }
4376
4377                         printf("%s,%s%s vs. %s,%s%s %s => %s\n",
4378                                 wrepl_name_type_string(records[i].r1.type),
4379                                 wrepl_name_state_string(records[i].r1.state),
4380                                 (records[i].r1.is_static?",static":""),
4381                                 wrepl_name_type_string(records[i].r2.type),
4382                                 wrepl_name_state_string(records[i].r2.state),
4383                                 (records[i].r2.is_static?",static":""),
4384                                 (records[i].comment?records[i].comment:ips),
4385                                 expected);
4386                 }
4387
4388                 /*
4389                  * Setup R1
4390                  */
4391                 wins_name_r1->name      = &records[i].name;
4392                 wins_name_r1->flags     = WREPL_NAME_FLAGS(records[i].r1.type,
4393                                                            records[i].r1.state,
4394                                                            records[i].r1.node,
4395                                                            records[i].r1.is_static);
4396                 wins_name_r1->id        = ++records[i].r1.owner->max_version;
4397                 if (wins_name_r1->flags & 2) {
4398                         wins_name_r1->addresses.addresses.num_ips = records[i].r1.num_ips;
4399                         wins_name_r1->addresses.addresses.ips     = discard_const(records[i].r1.ips);
4400                 } else {
4401                         wins_name_r1->addresses.ip = records[i].r1.ips[0].ip;
4402                 }
4403                 wins_name_r1->unknown   = "255.255.255.255";
4404
4405                 /* now apply R1 */
4406                 ret &= test_wrepl_update_one(ctx, records[i].r1.owner, wins_name_r1);
4407                 ret &= test_wrepl_is_applied(ctx, records[i].r1.owner,
4408                                              wins_name_r1, records[i].r1.apply_expected);
4409
4410                 /*
4411                  * Setup R2
4412                  */
4413                 wins_name_r2->name      = &records[i].name;
4414                 wins_name_r2->flags     = WREPL_NAME_FLAGS(records[i].r2.type,
4415                                                            records[i].r2.state,
4416                                                            records[i].r2.node,
4417                                                            records[i].r2.is_static);
4418                 wins_name_r2->id        = ++records[i].r2.owner->max_version;
4419                 if (wins_name_r2->flags & 2) {
4420                         wins_name_r2->addresses.addresses.num_ips = records[i].r2.num_ips;
4421                         wins_name_r2->addresses.addresses.ips     = discard_const(records[i].r2.ips);
4422                 } else {
4423                         wins_name_r2->addresses.ip = records[i].r2.ips[0].ip;
4424                 }
4425                 wins_name_r2->unknown   = "255.255.255.255";
4426
4427                 /* now apply R2 */
4428                 ret &= test_wrepl_update_one(ctx, records[i].r2.owner, wins_name_r2);
4429                 if (records[i].r1.state == WREPL_STATE_RELEASED) {
4430                         ret &= test_wrepl_is_applied(ctx, records[i].r1.owner,
4431                                                      wins_name_r1, False);
4432                 } else if (records[i].r2.sgroup_merge) {
4433                         ret &= test_wrepl_sgroup_merged(ctx, records[i].r2.merge_owner,
4434                                                         records[i].r1.owner,
4435                                                         records[i].r1.num_ips, records[i].r1.ips,
4436                                                         records[i].r2.owner,
4437                                                         records[i].r2.num_ips, records[i].r2.ips,
4438                                                         wins_name_r2);
4439                 } else if (records[i].r1.owner != records[i].r2.owner) {
4440                         BOOL _expected;
4441                         _expected = (records[i].r1.apply_expected && !records[i].r2.apply_expected);
4442                         ret &= test_wrepl_is_applied(ctx, records[i].r1.owner,
4443                                                      wins_name_r1, _expected);
4444                 }
4445                 if (records[i].r2.state == WREPL_STATE_RELEASED) {
4446                         ret &= test_wrepl_is_applied(ctx, records[i].r2.owner,
4447                                                      wins_name_r2, False);
4448                 } else if (!records[i].r2.sgroup_merge) {
4449                         ret &= test_wrepl_is_applied(ctx, records[i].r2.owner,
4450                                                      wins_name_r2, records[i].r2.apply_expected);
4451                 }
4452
4453                 if (records[i].r2.sgroup_cleanup) {
4454                         /* clean up the SGROUP record */
4455                         wins_name_r1->name      = &records[i].name;
4456                         wins_name_r1->flags     = WREPL_NAME_FLAGS(WREPL_TYPE_SGROUP,
4457                                                                    WREPL_STATE_ACTIVE,
4458                                                                    WREPL_NODE_B, False);
4459                         wins_name_r1->id        = ++records[i].r1.owner->max_version;
4460                         wins_name_r1->addresses.addresses.num_ips = 0;
4461                         wins_name_r1->addresses.addresses.ips     = NULL;
4462                         wins_name_r1->unknown   = "255.255.255.255";
4463                         ret &= test_wrepl_update_one(ctx, records[i].r1.owner, wins_name_r1);
4464
4465                         /* here we test how names from an owner are deleted */
4466                         if (records[i].r2.sgroup_merge && records[i].r2.num_ips) {
4467                                 ret &= test_wrepl_sgroup_merged(ctx, NULL,
4468                                                                 records[i].r2.owner,
4469                                                                 records[i].r2.num_ips, records[i].r2.ips,
4470                                                                 records[i].r1.owner,
4471                                                                 0, NULL,
4472                                                                 wins_name_r2);
4473                         }
4474
4475                         /* clean up the SGROUP record */
4476                         wins_name_r2->name      = &records[i].name;
4477                         wins_name_r2->flags     = WREPL_NAME_FLAGS(WREPL_TYPE_SGROUP,
4478                                                                    WREPL_STATE_ACTIVE,
4479                                                                    WREPL_NODE_B, False);
4480                         wins_name_r2->id        = ++records[i].r2.owner->max_version;
4481                         wins_name_r2->addresses.addresses.num_ips = 0;
4482                         wins_name_r2->addresses.addresses.ips     = NULL;
4483                         wins_name_r2->unknown   = "255.255.255.255";
4484                         ret &= test_wrepl_update_one(ctx, records[i].r2.owner, wins_name_r2);
4485
4486                         /* take ownership of the SGROUP record */
4487                         wins_name_r2->name      = &records[i].name;
4488                         wins_name_r2->flags     = WREPL_NAME_FLAGS(WREPL_TYPE_SGROUP,
4489                                                                    WREPL_STATE_ACTIVE,
4490                                                                    WREPL_NODE_B, False);
4491                         wins_name_r2->id        = ++records[i].r2.owner->max_version;
4492                         wins_name_r2->addresses.addresses.num_ips = ARRAY_SIZE(addresses_B_1);
4493                         wins_name_r2->addresses.addresses.ips     = discard_const(addresses_B_1);
4494                         wins_name_r2->unknown   = "255.255.255.255";
4495                         ret &= test_wrepl_update_one(ctx, records[i].r2.owner, wins_name_r2);
4496                         ret &= test_wrepl_is_applied(ctx, records[i].r2.owner, wins_name_r2, True);
4497
4498                         /* overwrite the SGROUP record with unique,tombstone */
4499                         wins_name_r2->name      = &records[i].name;
4500                         wins_name_r2->flags     = WREPL_NAME_FLAGS(WREPL_TYPE_SGROUP,
4501                                                                    WREPL_STATE_TOMBSTONE,
4502                                                                    WREPL_NODE_B, False);
4503                         wins_name_r2->id        = ++records[i].r2.owner->max_version;
4504                         wins_name_r2->addresses.addresses.num_ips = ARRAY_SIZE(addresses_B_1);
4505                         wins_name_r2->addresses.addresses.ips     = discard_const(addresses_B_1);
4506                         wins_name_r2->unknown   = "255.255.255.255";
4507                         ret &= test_wrepl_update_one(ctx, records[i].r2.owner, wins_name_r2);
4508                         ret &= test_wrepl_is_applied(ctx, records[i].r2.owner, wins_name_r2, True);
4509                 }
4510
4511                 /* the first one is a cleanup run */
4512                 if (!ret && i == 0) ret = True;
4513
4514                 if (!ret) {
4515                         printf("conflict handled wrong or record[%u]: %s\n", i, records[i].line);
4516                         return ret;
4517                 }
4518         }
4519
4520         return ret;
4521 }
4522
4523 static BOOL test_conflict_owned_released_vs_replica(struct test_wrepl_conflict_conn *ctx)
4524 {
4525         BOOL ret = True;
4526         NTSTATUS status;
4527         struct wrepl_wins_name wins_name_;
4528         struct wrepl_wins_name *wins_name = &wins_name_;
4529         struct nbt_name_register name_register_;
4530         struct nbt_name_register *name_register = &name_register_;
4531         struct nbt_name_release release_;
4532         struct nbt_name_release *release = &release_;
4533         uint32_t i;
4534         struct {
4535                 const char *line; /* just better debugging */
4536                 struct nbt_name name;
4537                 struct {
4538                         uint32_t nb_flags;
4539                         BOOL mhomed;
4540                         uint32_t num_ips;
4541                         const struct wrepl_ip *ips;
4542                         BOOL apply_expected;
4543                 } wins;
4544                 struct {
4545                         enum wrepl_name_type type;
4546                         enum wrepl_name_state state;
4547                         enum wrepl_name_node node;
4548                         BOOL is_static;
4549                         uint32_t num_ips;
4550                         const struct wrepl_ip *ips;
4551                         BOOL apply_expected;
4552                 } replica;
4553         } records[] = {
4554 /* 
4555  * unique vs. unique section
4556  */
4557         /*
4558          * unique,released vs. unique,active with same ip(s)
4559          */
4560         {
4561                 .line   = __location__,
4562                 .name   = _NBT_NAME("_UR_UA_SI", 0x00, NULL),
4563                 .wins   = {
4564                         .nb_flags       = 0,
4565                         .mhomed         = False,
4566                         .num_ips        = ctx->addresses_best_num,
4567                         .ips            = ctx->addresses_best,
4568                         .apply_expected = True
4569                 },
4570                 .replica= {
4571                         .type           = WREPL_TYPE_UNIQUE,
4572                         .state          = WREPL_STATE_ACTIVE,
4573                         .node           = WREPL_NODE_B,
4574                         .is_static      = False,
4575                         .num_ips        = ctx->addresses_best_num,
4576                         .ips            = ctx->addresses_best,
4577                         .apply_expected = True
4578                 },
4579         },
4580         /*
4581          * unique,released vs. unique,active with different ip(s)
4582          */
4583         {
4584                 .line   = __location__,
4585                 .name   = _NBT_NAME("_UR_UA_DI", 0x00, NULL),
4586                 .wins   = {
4587                         .nb_flags       = 0,
4588                         .mhomed         = False,
4589                         .num_ips        = ctx->addresses_best_num,
4590                         .ips            = ctx->addresses_best,
4591                         .apply_expected = True
4592                 },
4593                 .replica= {
4594                         .type           = WREPL_TYPE_UNIQUE,
4595                         .state          = WREPL_STATE_ACTIVE,
4596                         .node           = WREPL_NODE_B,
4597                         .is_static      = False,
4598                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4599                         .ips            = addresses_B_1,
4600                         .apply_expected = True
4601                 },
4602         },
4603         /*
4604          * unique,released vs. unique,tombstone with same ip(s)
4605          */
4606         {
4607                 .line   = __location__,
4608                 .name   = _NBT_NAME("_UR_UT_SI", 0x00, NULL),
4609                 .wins   = {
4610                         .nb_flags       = 0,
4611                         .mhomed         = False,
4612                         .num_ips        = ctx->addresses_best_num,
4613                         .ips            = ctx->addresses_best,
4614                         .apply_expected = True
4615                 },
4616                 .replica= {
4617                         .type           = WREPL_TYPE_UNIQUE,
4618                         .state          = WREPL_STATE_TOMBSTONE,
4619                         .node           = WREPL_NODE_B,
4620                         .is_static      = False,
4621                         .num_ips        = ctx->addresses_best_num,
4622                         .ips            = ctx->addresses_best,
4623                         .apply_expected = True
4624                 },
4625         },
4626         /*
4627          * unique,released vs. unique,tombstone with different ip(s)
4628          */
4629         {
4630                 .line   = __location__,
4631                 .name   = _NBT_NAME("_UR_UT_DI", 0x00, NULL),
4632                 .wins   = {
4633                         .nb_flags       = 0,
4634                         .mhomed         = False,
4635                         .num_ips        = ctx->addresses_best_num,
4636                         .ips            = ctx->addresses_best,
4637                         .apply_expected = True
4638                 },
4639                 .replica= {
4640                         .type           = WREPL_TYPE_UNIQUE,
4641                         .state          = WREPL_STATE_TOMBSTONE,
4642                         .node           = WREPL_NODE_B,
4643                         .is_static      = False,
4644                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4645                         .ips            = addresses_B_1,
4646                         .apply_expected = True
4647                 },
4648         },
4649 /* 
4650  * unique vs. group section
4651  */
4652         /*
4653          * unique,released vs. group,active with same ip(s)
4654          */
4655         {
4656                 .line   = __location__,
4657                 .name   = _NBT_NAME("_UR_GA_SI", 0x00, NULL),
4658                 .wins   = {
4659                         .nb_flags       = 0,
4660                         .mhomed         = False,
4661                         .num_ips        = ctx->addresses_best_num,
4662                         .ips            = ctx->addresses_best,
4663                         .apply_expected = True
4664                 },
4665                 .replica= {
4666                         .type           = WREPL_TYPE_GROUP,
4667                         .state          = WREPL_STATE_ACTIVE,
4668                         .node           = WREPL_NODE_B,
4669                         .is_static      = False,
4670                         .num_ips        = ctx->addresses_best_num,
4671                         .ips            = ctx->addresses_best,
4672                         .apply_expected = True
4673                 },
4674         },
4675         /*
4676          * unique,released vs. group,active with different ip(s)
4677          */
4678         {
4679                 .line   = __location__,
4680                 .name   = _NBT_NAME("_UR_GA_DI", 0x00, NULL),
4681                 .wins   = {
4682                         .nb_flags       = 0,
4683                         .mhomed         = False,
4684                         .num_ips        = ctx->addresses_best_num,
4685                         .ips            = ctx->addresses_best,
4686                         .apply_expected = True
4687                 },
4688                 .replica= {
4689                         .type           = WREPL_TYPE_GROUP,
4690                         .state          = WREPL_STATE_ACTIVE,
4691                         .node           = WREPL_NODE_B,
4692                         .is_static      = False,
4693                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4694                         .ips            = addresses_B_1,
4695                         .apply_expected = True
4696                 },
4697         },
4698         /*
4699          * unique,released vs. group,tombstone with same ip(s)
4700          */
4701         {
4702                 .line   = __location__,
4703                 .name   = _NBT_NAME("_UR_GT_SI", 0x00, NULL),
4704                 .wins   = {
4705                         .nb_flags       = 0,
4706                         .mhomed         = False,
4707                         .num_ips        = ctx->addresses_best_num,
4708                         .ips            = ctx->addresses_best,
4709                         .apply_expected = True
4710                 },
4711                 .replica= {
4712                         .type           = WREPL_TYPE_GROUP,
4713                         .state          = WREPL_STATE_TOMBSTONE,
4714                         .node           = WREPL_NODE_B,
4715                         .is_static      = False,
4716                         .num_ips        = ctx->addresses_best_num,
4717                         .ips            = ctx->addresses_best,
4718                         .apply_expected = True
4719                 },
4720         },
4721         /*
4722          * unique,released vs. group,tombstone with different ip(s)
4723          */
4724         {
4725                 .line   = __location__,
4726                 .name   = _NBT_NAME("_UR_GT_DI", 0x00, NULL),
4727                 .wins   = {
4728                         .nb_flags       = 0,
4729                         .mhomed         = False,
4730                         .num_ips        = ctx->addresses_best_num,
4731                         .ips            = ctx->addresses_best,
4732                         .apply_expected = True
4733                 },
4734                 .replica= {
4735                         .type           = WREPL_TYPE_GROUP,
4736                         .state          = WREPL_STATE_TOMBSTONE,
4737                         .node           = WREPL_NODE_B,
4738                         .is_static      = False,
4739                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4740                         .ips            = addresses_B_1,
4741                         .apply_expected = True
4742                 },
4743         },
4744 /* 
4745  * unique vs. special group section
4746  */
4747         /*
4748          * unique,released vs. sgroup,active with same ip(s)
4749          */
4750         {
4751                 .line   = __location__,
4752                 .name   = _NBT_NAME("_UR_SA_SI", 0x00, NULL),
4753                 .wins   = {
4754                         .nb_flags       = 0,
4755                         .mhomed         = False,
4756                         .num_ips        = ctx->addresses_best_num,
4757                         .ips            = ctx->addresses_best,
4758                         .apply_expected = True
4759                 },
4760                 .replica= {
4761                         .type           = WREPL_TYPE_SGROUP,
4762                         .state          = WREPL_STATE_ACTIVE,
4763                         .node           = WREPL_NODE_B,
4764                         .is_static      = False,
4765                         .num_ips        = ctx->addresses_best_num,
4766                         .ips            = ctx->addresses_best,
4767                         .apply_expected = True
4768                 },
4769         },
4770         /*
4771          * unique,released vs. sgroup,active with different ip(s)
4772          */
4773         {
4774                 .line   = __location__,
4775                 .name   = _NBT_NAME("_UR_SA_DI", 0x00, NULL),
4776                 .wins   = {
4777                         .nb_flags       = 0,
4778                         .mhomed         = False,
4779                         .num_ips        = ctx->addresses_best_num,
4780                         .ips            = ctx->addresses_best,
4781                         .apply_expected = True
4782                 },
4783                 .replica= {
4784                         .type           = WREPL_TYPE_SGROUP,
4785                         .state          = WREPL_STATE_ACTIVE,
4786                         .node           = WREPL_NODE_B,
4787                         .is_static      = False,
4788                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4789                         .ips            = addresses_B_1,
4790                         .apply_expected = True
4791                 },
4792         },
4793         /*
4794          * unique,released vs. sgroup,tombstone with same ip(s)
4795          */
4796         {
4797                 .line   = __location__,
4798                 .name   = _NBT_NAME("_UR_ST_SI", 0x00, NULL),
4799                 .wins   = {
4800                         .nb_flags       = 0,
4801                         .mhomed         = False,
4802                         .num_ips        = ctx->addresses_best_num,
4803                         .ips            = ctx->addresses_best,
4804                         .apply_expected = True
4805                 },
4806                 .replica= {
4807                         .type           = WREPL_TYPE_SGROUP,
4808                         .state          = WREPL_STATE_TOMBSTONE,
4809                         .node           = WREPL_NODE_B,
4810                         .is_static      = False,
4811                         .num_ips        = ctx->addresses_best_num,
4812                         .ips            = ctx->addresses_best,
4813                         .apply_expected = True
4814                 },
4815         },
4816         /*
4817          * unique,released vs. sgroup,tombstone with different ip(s)
4818          */
4819         {
4820                 .line   = __location__,
4821                 .name   = _NBT_NAME("_UR_ST_DI", 0x00, NULL),
4822                 .wins   = {
4823                         .nb_flags       = 0,
4824                         .mhomed         = False,
4825                         .num_ips        = ctx->addresses_best_num,
4826                         .ips            = ctx->addresses_best,
4827                         .apply_expected = True
4828                 },
4829                 .replica= {
4830                         .type           = WREPL_TYPE_SGROUP,
4831                         .state          = WREPL_STATE_TOMBSTONE,
4832                         .node           = WREPL_NODE_B,
4833                         .is_static      = False,
4834                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4835                         .ips            = addresses_B_1,
4836                         .apply_expected = True
4837                 },
4838         },
4839 /* 
4840  * unique vs. multi homed section
4841  */
4842         /*
4843          * unique,released vs. mhomed,active with same ip(s)
4844          */
4845         {
4846                 .line   = __location__,
4847                 .name   = _NBT_NAME("_UR_MA_SI", 0x00, NULL),
4848                 .wins   = {
4849                         .nb_flags       = 0,
4850                         .mhomed         = False,
4851                         .num_ips        = ctx->addresses_best_num,
4852                         .ips            = ctx->addresses_best,
4853                         .apply_expected = True
4854                 },
4855                 .replica= {
4856                         .type           = WREPL_TYPE_MHOMED,
4857                         .state          = WREPL_STATE_ACTIVE,
4858                         .node           = WREPL_NODE_B,
4859                         .is_static      = False,
4860                         .num_ips        = ctx->addresses_best_num,
4861                         .ips            = ctx->addresses_best,
4862                         .apply_expected = True
4863                 },
4864         },
4865         /*
4866          * unique,released vs. mhomed,active with different ip(s)
4867          */
4868         {
4869                 .line   = __location__,
4870                 .name   = _NBT_NAME("_UR_MA_DI", 0x00, NULL),
4871                 .wins   = {
4872                         .nb_flags       = 0,
4873                         .mhomed         = False,
4874                         .num_ips        = ctx->addresses_best_num,
4875                         .ips            = ctx->addresses_best,
4876                         .apply_expected = True
4877                 },
4878                 .replica= {
4879                         .type           = WREPL_TYPE_MHOMED,
4880                         .state          = WREPL_STATE_ACTIVE,
4881                         .node           = WREPL_NODE_B,
4882                         .is_static      = False,
4883                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4884                         .ips            = addresses_B_1,
4885                         .apply_expected = True
4886                 },
4887         },
4888         /*
4889          * unique,released vs. mhomed,tombstone with same ip(s)
4890          */
4891         {
4892                 .line   = __location__,
4893                 .name   = _NBT_NAME("_UR_MT_SI", 0x00, NULL),
4894                 .wins   = {
4895                         .nb_flags       = 0,
4896                         .mhomed         = False,
4897                         .num_ips        = ctx->addresses_best_num,
4898                         .ips            = ctx->addresses_best,
4899                         .apply_expected = True
4900                 },
4901                 .replica= {
4902                         .type           = WREPL_TYPE_MHOMED,
4903                         .state          = WREPL_STATE_TOMBSTONE,
4904                         .node           = WREPL_NODE_B,
4905                         .is_static      = False,
4906                         .num_ips        = ctx->addresses_best_num,
4907                         .ips            = ctx->addresses_best,
4908                         .apply_expected = True
4909                 },
4910         },
4911         /*
4912          * unique,released vs. mhomed,tombstone with different ip(s)
4913          */
4914         {
4915                 .line   = __location__,
4916                 .name   = _NBT_NAME("_UR_MT_DI", 0x00, NULL),
4917                 .wins   = {
4918                         .nb_flags       = 0,
4919                         .mhomed         = False,
4920                         .num_ips        = ctx->addresses_best_num,
4921                         .ips            = ctx->addresses_best,
4922                         .apply_expected = True
4923                 },
4924                 .replica= {
4925                         .type           = WREPL_TYPE_MHOMED,
4926                         .state          = WREPL_STATE_TOMBSTONE,
4927                         .node           = WREPL_NODE_B,
4928                         .is_static      = False,
4929                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4930                         .ips            = addresses_B_1,
4931                         .apply_expected = True
4932                 },
4933         },
4934 /* 
4935  * group vs. unique section
4936  */
4937         /*
4938          * group,released vs. unique,active with same ip(s)
4939          */
4940         {
4941                 .line   = __location__,
4942                 .name   = _NBT_NAME("_GR_UA_SI", 0x00, NULL),
4943                 .wins   = {
4944                         .nb_flags       = NBT_NM_GROUP,
4945                         .mhomed         = False,
4946                         .num_ips        = ctx->addresses_best_num,
4947                         .ips            = ctx->addresses_best,
4948                         .apply_expected = True
4949                 },
4950                 .replica= {
4951                         .type           = WREPL_TYPE_UNIQUE,
4952                         .state          = WREPL_STATE_ACTIVE,
4953                         .node           = WREPL_NODE_B,
4954                         .is_static      = False,
4955                         .num_ips        = ctx->addresses_best_num,
4956                         .ips            = ctx->addresses_best,
4957                         .apply_expected = False
4958                 },
4959         },
4960         /*
4961          * group,released vs. unique,active with different ip(s)
4962          */
4963         {
4964                 .line   = __location__,
4965                 .name   = _NBT_NAME("_GR_UA_DI", 0x00, NULL),
4966                 .wins   = {
4967                         .nb_flags       = NBT_NM_GROUP,
4968                         .mhomed         = False,
4969                         .num_ips        = ctx->addresses_best_num,
4970                         .ips            = ctx->addresses_best,
4971                         .apply_expected = True
4972                 },
4973                 .replica= {
4974                         .type           = WREPL_TYPE_UNIQUE,
4975                         .state          = WREPL_STATE_ACTIVE,
4976                         .node           = WREPL_NODE_B,
4977                         .is_static      = False,
4978                         .num_ips        = ARRAY_SIZE(addresses_B_1),
4979                         .ips            = addresses_B_1,
4980                         .apply_expected = False
4981                 },
4982         },
4983         /*
4984          * group,released vs. unique,tombstone with same ip(s)
4985          */
4986         {
4987                 .line   = __location__,
4988                 .name   = _NBT_NAME("_GR_UT_SI", 0x00, NULL),
4989                 .wins   = {
4990                         .nb_flags       = NBT_NM_GROUP,
4991                         .mhomed         = False,
4992                         .num_ips        = ctx->addresses_best_num,
4993                         .ips            = ctx->addresses_best,
4994                         .apply_expected = True
4995                 },
4996                 .replica= {
4997                         .type           = WREPL_TYPE_UNIQUE,
4998                         .state          = WREPL_STATE_TOMBSTONE,
4999                         .node           = WREPL_NODE_B,
5000                         .is_static      = False,
5001                         .num_ips        = ctx->addresses_best_num,
5002                         .ips            = ctx->addresses_best,
5003                         .apply_expected = False
5004                 },
5005         },
5006         /*
5007          * group,released vs. unique,tombstone with different ip(s)
5008          */
5009         {
5010                 .line   = __location__,
5011                 .name   = _NBT_NAME("_GR_UT_DI", 0x00, NULL),
5012                 .wins   = {
5013                         .nb_flags       = NBT_NM_GROUP,
5014                         .mhomed         = False,
5015                         .num_ips        = ctx->addresses_best_num,
5016                         .ips            = ctx->addresses_best,
5017                         .apply_expected = True
5018                 },
5019                 .replica= {
5020                         .type           = WREPL_TYPE_UNIQUE,
5021                         .state          = WREPL_STATE_TOMBSTONE,
5022                         .node           = WREPL_NODE_B,
5023                         .is_static      = False,
5024                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5025                         .ips            = addresses_B_1,
5026                         .apply_expected = False
5027                 },
5028         },
5029 /* 
5030  * group vs. group section
5031  */
5032         /*
5033          * group,released vs. group,active with same ip(s)
5034          */
5035         {
5036                 .line   = __location__,
5037                 .name   = _NBT_NAME("_GR_GA_SI", 0x00, NULL),
5038                 .wins   = {
5039                         .nb_flags       = NBT_NM_GROUP,
5040                         .mhomed         = False,
5041                         .num_ips        = ctx->addresses_best_num,
5042                         .ips            = ctx->addresses_best,
5043                         .apply_expected = True
5044                 },
5045                 .replica= {
5046                         .type           = WREPL_TYPE_GROUP,
5047                         .state          = WREPL_STATE_ACTIVE,
5048                         .node           = WREPL_NODE_B,
5049                         .is_static      = False,
5050                         .num_ips        = ctx->addresses_best_num,
5051                         .ips            = ctx->addresses_best,
5052                         .apply_expected = True
5053                 },
5054         },
5055         /*
5056          * group,released vs. group,active with different ip(s)
5057          */
5058         {
5059                 .line   = __location__,
5060                 .name   = _NBT_NAME("_GR_GA_DI", 0x00, NULL),
5061                 .wins   = {
5062                         .nb_flags       = NBT_NM_GROUP,
5063                         .mhomed         = False,
5064                         .num_ips        = ctx->addresses_best_num,
5065                         .ips            = ctx->addresses_best,
5066                         .apply_expected = True
5067                 },
5068                 .replica= {
5069                         .type           = WREPL_TYPE_GROUP,
5070                         .state          = WREPL_STATE_ACTIVE,
5071                         .node           = WREPL_NODE_B,
5072                         .is_static      = False,
5073                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5074                         .ips            = addresses_B_1,
5075                         .apply_expected = True
5076                 },
5077         },
5078         /*
5079          * group,released vs. group,tombstone with same ip(s)
5080          */
5081         {
5082                 .line   = __location__,
5083                 .name   = _NBT_NAME("_GR_GT_SI", 0x00, NULL),
5084                 .wins   = {
5085                         .nb_flags       = NBT_NM_GROUP,
5086                         .mhomed         = False,
5087                         .num_ips        = ctx->addresses_best_num,
5088                         .ips            = ctx->addresses_best,
5089                         .apply_expected = True
5090                 },
5091                 .replica= {
5092                         .type           = WREPL_TYPE_GROUP,
5093                         .state          = WREPL_STATE_TOMBSTONE,
5094                         .node           = WREPL_NODE_B,
5095                         .is_static      = False,
5096                         .num_ips        = ctx->addresses_best_num,
5097                         .ips            = ctx->addresses_best,
5098                         .apply_expected = True
5099                 },
5100         },
5101         /*
5102          * group,released vs. group,tombstone with different ip(s)
5103          */
5104         {
5105                 .line   = __location__,
5106                 .name   = _NBT_NAME("_GR_GT_DI", 0x00, NULL),
5107                 .wins   = {
5108                         .nb_flags       = NBT_NM_GROUP,
5109                         .mhomed         = False,
5110                         .num_ips        = ctx->addresses_best_num,
5111                         .ips            = ctx->addresses_best,
5112                         .apply_expected = True
5113                 },
5114                 .replica= {
5115                         .type           = WREPL_TYPE_GROUP,
5116                         .state          = WREPL_STATE_TOMBSTONE,
5117                         .node           = WREPL_NODE_B,
5118                         .is_static      = False,
5119                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5120                         .ips            = addresses_B_1,
5121                         .apply_expected = True
5122                 },
5123         },
5124 /* 
5125  * group vs. special group section
5126  */
5127         /*
5128          * group,released vs. sgroup,active with same ip(s)
5129          */
5130         {
5131                 .line   = __location__,
5132                 .name   = _NBT_NAME("_GR_SA_SI", 0x00, NULL),
5133                 .wins   = {
5134                         .nb_flags       = NBT_NM_GROUP,
5135                         .mhomed         = False,
5136                         .num_ips        = ctx->addresses_best_num,
5137                         .ips            = ctx->addresses_best,
5138                         .apply_expected = True
5139                 },
5140                 .replica= {
5141                         .type           = WREPL_TYPE_SGROUP,
5142                         .state          = WREPL_STATE_ACTIVE,
5143                         .node           = WREPL_NODE_B,
5144                         .is_static      = False,
5145                         .num_ips        = ctx->addresses_best_num,
5146                         .ips            = ctx->addresses_best,
5147                         .apply_expected = False
5148                 },
5149         },
5150         /*
5151          * group,released vs. sgroup,active with different ip(s)
5152          */
5153         {
5154                 .line   = __location__,
5155                 .name   = _NBT_NAME("_GR_SA_DI", 0x00, NULL),
5156                 .wins   = {
5157                         .nb_flags       = NBT_NM_GROUP,
5158                         .mhomed         = False,
5159                         .num_ips        = ctx->addresses_best_num,
5160                         .ips            = ctx->addresses_best,
5161                         .apply_expected = True
5162                 },
5163                 .replica= {
5164                         .type           = WREPL_TYPE_SGROUP,
5165                         .state          = WREPL_STATE_ACTIVE,
5166                         .node           = WREPL_NODE_B,
5167                         .is_static      = False,
5168                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5169                         .ips            = addresses_B_1,
5170                         .apply_expected = False
5171                 },
5172         },
5173         /*
5174          * group,released vs. sgroup,tombstone with same ip(s)
5175          */
5176         {
5177                 .line   = __location__,
5178                 .name   = _NBT_NAME("_GR_ST_SI", 0x00, NULL),
5179                 .wins   = {
5180                         .nb_flags       = NBT_NM_GROUP,
5181                         .mhomed         = False,
5182                         .num_ips        = ctx->addresses_best_num,
5183                         .ips            = ctx->addresses_best,
5184                         .apply_expected = True
5185                 },
5186                 .replica= {
5187                         .type           = WREPL_TYPE_SGROUP,
5188                         .state          = WREPL_STATE_TOMBSTONE,
5189                         .node           = WREPL_NODE_B,
5190                         .is_static      = False,
5191                         .num_ips        = ctx->addresses_best_num,
5192                         .ips            = ctx->addresses_best,
5193                         .apply_expected = False
5194                 },
5195         },
5196         /*
5197          * group,released vs. sgroup,tombstone with different ip(s)
5198          */
5199         {
5200                 .line   = __location__,
5201                 .name   = _NBT_NAME("_GR_ST_DI", 0x00, NULL),
5202                 .wins   = {
5203                         .nb_flags       = NBT_NM_GROUP,
5204                         .mhomed         = False,
5205                         .num_ips        = ctx->addresses_best_num,
5206                         .ips            = ctx->addresses_best,
5207                         .apply_expected = True
5208                 },
5209                 .replica= {
5210                         .type           = WREPL_TYPE_SGROUP,
5211                         .state          = WREPL_STATE_TOMBSTONE,
5212                         .node           = WREPL_NODE_B,
5213                         .is_static      = False,
5214                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5215                         .ips            = addresses_B_1,
5216                         .apply_expected = False
5217                 },
5218         },
5219 /* 
5220  * group vs. multi homed section
5221  */
5222         /*
5223          * group,released vs. mhomed,active with same ip(s)
5224          */
5225         {
5226                 .line   = __location__,
5227                 .name   = _NBT_NAME("_GR_MA_SI", 0x00, NULL),
5228                 .wins   = {
5229                         .nb_flags       = NBT_NM_GROUP,
5230                         .mhomed         = False,
5231                         .num_ips        = ctx->addresses_best_num,
5232                         .ips            = ctx->addresses_best,
5233                         .apply_expected = True
5234                 },
5235                 .replica= {
5236                         .type           = WREPL_TYPE_MHOMED,
5237                         .state          = WREPL_STATE_ACTIVE,
5238                         .node           = WREPL_NODE_B,
5239                         .is_static      = False,
5240                         .num_ips        = ctx->addresses_best_num,
5241                         .ips            = ctx->addresses_best,
5242                         .apply_expected = False
5243                 },
5244         },
5245         /*
5246          * group,released vs. mhomed,active with different ip(s)
5247          */
5248         {
5249                 .line   = __location__,
5250                 .name   = _NBT_NAME("_GR_MA_DI", 0x00, NULL),
5251                 .wins   = {
5252                         .nb_flags       = NBT_NM_GROUP,
5253                         .mhomed         = False,
5254                         .num_ips        = ctx->addresses_best_num,
5255                         .ips            = ctx->addresses_best,
5256                         .apply_expected = True
5257                 },
5258                 .replica= {
5259                         .type           = WREPL_TYPE_MHOMED,
5260                         .state          = WREPL_STATE_ACTIVE,
5261                         .node           = WREPL_NODE_B,
5262                         .is_static      = False,
5263                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5264                         .ips            = addresses_B_1,
5265                         .apply_expected = False
5266                 },
5267         },
5268         /*
5269          * group,released vs. mhomed,tombstone with same ip(s)
5270          */
5271         {
5272                 .line   = __location__,
5273                 .name   = _NBT_NAME("_GR_MT_SI", 0x00, NULL),
5274                 .wins   = {
5275                         .nb_flags       = NBT_NM_GROUP,
5276                         .mhomed         = False,
5277                         .num_ips        = ctx->addresses_best_num,
5278                         .ips            = ctx->addresses_best,
5279                         .apply_expected = True
5280                 },
5281                 .replica= {
5282                         .type           = WREPL_TYPE_MHOMED,
5283                         .state          = WREPL_STATE_TOMBSTONE,
5284                         .node           = WREPL_NODE_B,
5285                         .is_static      = False,
5286                         .num_ips        = ctx->addresses_best_num,
5287                         .ips            = ctx->addresses_best,
5288                         .apply_expected = False
5289                 },
5290         },
5291         /*
5292          * group,released vs. mhomed,tombstone with different ip(s)
5293          */
5294         {
5295                 .line   = __location__,
5296                 .name   = _NBT_NAME("_GR_MT_DI", 0x00, NULL),
5297                 .wins   = {
5298                         .nb_flags       = NBT_NM_GROUP,
5299                         .mhomed         = False,
5300                         .num_ips        = ctx->addresses_best_num,
5301                         .ips            = ctx->addresses_best,
5302                         .apply_expected = True
5303                 },
5304                 .replica= {
5305                         .type           = WREPL_TYPE_MHOMED,
5306                         .state          = WREPL_STATE_TOMBSTONE,
5307                         .node           = WREPL_NODE_B,
5308                         .is_static      = False,
5309                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5310                         .ips            = addresses_B_1,
5311                         .apply_expected = False
5312                 },
5313         },
5314 /* 
5315  * special group vs. unique section
5316  */
5317         /*
5318          * sgroup,released vs. unique,active with same ip(s)
5319          */
5320         {
5321                 .line   = __location__,
5322                 .name   = _NBT_NAME("_SR_UA_SI", 0x1C, NULL),
5323                 .wins   = {
5324                         .nb_flags       = NBT_NM_GROUP,
5325                         .mhomed         = False,
5326                         .num_ips        = ctx->addresses_best_num,
5327                         .ips            = ctx->addresses_best,
5328                         .apply_expected = True
5329                 },
5330                 .replica= {
5331                         .type           = WREPL_TYPE_UNIQUE,
5332                         .state          = WREPL_STATE_ACTIVE,
5333                         .node           = WREPL_NODE_B,
5334                         .is_static      = False,
5335                         .num_ips        = ctx->addresses_best_num,
5336                         .ips            = ctx->addresses_best,
5337                         .apply_expected = True
5338                 },
5339         },
5340         /*
5341          * sgroup,released vs. unique,active with different ip(s)
5342          */
5343         {
5344                 .line   = __location__,
5345                 .name   = _NBT_NAME("_SR_UA_DI", 0x1C, NULL),
5346                 .wins   = {
5347                         .nb_flags       = NBT_NM_GROUP,
5348                         .mhomed         = False,
5349                         .num_ips        = ctx->addresses_best_num,
5350                         .ips            = ctx->addresses_best,
5351                         .apply_expected = True
5352                 },
5353                 .replica= {
5354                         .type           = WREPL_TYPE_UNIQUE,
5355                         .state          = WREPL_STATE_ACTIVE,
5356                         .node           = WREPL_NODE_B,
5357                         .is_static      = False,
5358                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5359                         .ips            = addresses_B_1,
5360                         .apply_expected = True
5361                 },
5362         },
5363         /*
5364          * sgroup,released vs. unique,tombstone with same ip(s)
5365          */
5366         {
5367                 .line   = __location__,
5368                 .name   = _NBT_NAME("_SR_UT_SI", 0x1C, NULL),
5369                 .wins   = {
5370                         .nb_flags       = NBT_NM_GROUP,
5371                         .mhomed         = False,
5372                         .num_ips        = ctx->addresses_best_num,
5373                         .ips            = ctx->addresses_best,
5374                         .apply_expected = True
5375                 },
5376                 .replica= {
5377                         .type           = WREPL_TYPE_UNIQUE,
5378                         .state          = WREPL_STATE_TOMBSTONE,
5379                         .node           = WREPL_NODE_B,
5380                         .is_static      = False,
5381                         .num_ips        = ctx->addresses_best_num,
5382                         .ips            = ctx->addresses_best,
5383                         .apply_expected = True
5384                 },
5385         },
5386         /*
5387          * sgroup,released vs. unique,tombstone with different ip(s)
5388          */
5389         {
5390                 .line   = __location__,
5391                 .name   = _NBT_NAME("_SR_UT_DI", 0x1C, NULL),
5392                 .wins   = {
5393                         .nb_flags       = NBT_NM_GROUP,
5394                         .mhomed         = False,
5395                         .num_ips        = ctx->addresses_best_num,
5396                         .ips            = ctx->addresses_best,
5397                         .apply_expected = True
5398                 },
5399                 .replica= {
5400                         .type           = WREPL_TYPE_UNIQUE,
5401                         .state          = WREPL_STATE_TOMBSTONE,
5402                         .node           = WREPL_NODE_B,
5403                         .is_static      = False,
5404                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5405                         .ips            = addresses_B_1,
5406                         .apply_expected = True
5407                 },
5408         },
5409 /* 
5410  * special group vs. group section
5411  */
5412         /*
5413          * sgroup,released vs. group,active with same ip(s)
5414          */
5415         {
5416                 .line   = __location__,
5417                 .name   = _NBT_NAME("_SR_GA_SI", 0x1C, NULL),
5418                 .wins   = {
5419                         .nb_flags       = NBT_NM_GROUP,
5420                         .mhomed         = False,
5421                         .num_ips        = ctx->addresses_best_num,
5422                         .ips            = ctx->addresses_best,
5423                         .apply_expected = True
5424                 },
5425                 .replica= {
5426                         .type           = WREPL_TYPE_GROUP,
5427                         .state          = WREPL_STATE_ACTIVE,
5428                         .node           = WREPL_NODE_B,
5429                         .is_static      = False,
5430                         .num_ips        = ctx->addresses_best_num,
5431                         .ips            = ctx->addresses_best,
5432                         .apply_expected = True
5433                 },
5434         },
5435         /*
5436          * sgroup,released vs. group,active with different ip(s)
5437          */
5438         {
5439                 .line   = __location__,
5440                 .name   = _NBT_NAME("_SR_GA_DI", 0x1C, NULL),
5441                 .wins   = {
5442                         .nb_flags       = NBT_NM_GROUP,
5443                         .mhomed         = False,
5444                         .num_ips        = ctx->addresses_best_num,
5445                         .ips            = ctx->addresses_best,
5446                         .apply_expected = True
5447                 },
5448                 .replica= {
5449                         .type           = WREPL_TYPE_GROUP,
5450                         .state          = WREPL_STATE_ACTIVE,
5451                         .node           = WREPL_NODE_B,
5452                         .is_static      = False,
5453                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5454                         .ips            = addresses_B_1,
5455                         .apply_expected = True
5456                 },
5457         },
5458         /*
5459          * sgroup,released vs. group,tombstone with same ip(s)
5460          */
5461         {
5462                 .line   = __location__,
5463                 .name   = _NBT_NAME("_SR_GT_SI", 0x1C, NULL),
5464                 .wins   = {
5465                         .nb_flags       = NBT_NM_GROUP,
5466                         .mhomed         = False,
5467                         .num_ips        = ctx->addresses_best_num,
5468                         .ips            = ctx->addresses_best,
5469                         .apply_expected = True
5470                 },
5471                 .replica= {
5472                         .type           = WREPL_TYPE_GROUP,
5473                         .state          = WREPL_STATE_TOMBSTONE,
5474                         .node           = WREPL_NODE_B,
5475                         .is_static      = False,
5476                         .num_ips        = ctx->addresses_best_num,
5477                         .ips            = ctx->addresses_best,
5478                         .apply_expected = True
5479                 },
5480         },
5481         /*
5482          * sgroup,released vs. group,tombstone with different ip(s)
5483          */
5484         {
5485                 .line   = __location__,
5486                 .name   = _NBT_NAME("_SR_GT_DI", 0x1C, NULL),
5487                 .wins   = {
5488                         .nb_flags       = NBT_NM_GROUP,
5489                         .mhomed         = False,
5490                         .num_ips        = ctx->addresses_best_num,
5491                         .ips            = ctx->addresses_best,
5492                         .apply_expected = True
5493                 },
5494                 .replica= {
5495                         .type           = WREPL_TYPE_GROUP,
5496                         .state          = WREPL_STATE_TOMBSTONE,
5497                         .node           = WREPL_NODE_B,
5498                         .is_static      = False,
5499                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5500                         .ips            = addresses_B_1,
5501                         .apply_expected = True
5502                 },
5503         },
5504 /* 
5505  * special group vs. special group section
5506  */
5507         /*
5508          * sgroup,released vs. sgroup,active with same ip(s)
5509          */
5510         {
5511                 .line   = __location__,
5512                 .name   = _NBT_NAME("_SR_SA_SI", 0x1C, NULL),
5513                 .wins   = {
5514                         .nb_flags       = NBT_NM_GROUP,
5515                         .mhomed         = False,
5516                         .num_ips        = ctx->addresses_best_num,
5517                         .ips            = ctx->addresses_best,
5518                         .apply_expected = True
5519                 },
5520                 .replica= {
5521                         .type           = WREPL_TYPE_SGROUP,
5522                         .state          = WREPL_STATE_ACTIVE,
5523                         .node           = WREPL_NODE_B,
5524                         .is_static      = False,
5525                         .num_ips        = ctx->addresses_best_num,
5526                         .ips            = ctx->addresses_best,
5527                         .apply_expected = True
5528                 },
5529         },
5530         /*
5531          * sgroup,released vs. sgroup,active with different ip(s)
5532          */
5533         {
5534                 .line   = __location__,
5535                 .name   = _NBT_NAME("_SR_SA_DI", 0x1C, NULL),
5536                 .wins   = {
5537                         .nb_flags       = NBT_NM_GROUP,
5538                         .mhomed         = False,
5539                         .num_ips        = ctx->addresses_best_num,
5540                         .ips            = ctx->addresses_best,
5541                         .apply_expected = True
5542                 },
5543                 .replica= {
5544                         .type           = WREPL_TYPE_SGROUP,
5545                         .state          = WREPL_STATE_ACTIVE,
5546                         .node           = WREPL_NODE_B,
5547                         .is_static      = False,
5548                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5549                         .ips            = addresses_B_1,
5550                         .apply_expected = True
5551                 },
5552         },
5553         /*
5554          * sgroup,released vs. sgroup,tombstone with same ip(s)
5555          */
5556         {
5557                 .line   = __location__,
5558                 .name   = _NBT_NAME("_SR_ST_SI", 0x1C, NULL),
5559                 .wins   = {
5560                         .nb_flags       = NBT_NM_GROUP,
5561                         .mhomed         = False,
5562                         .num_ips        = ctx->addresses_best_num,
5563                         .ips            = ctx->addresses_best,
5564                         .apply_expected = True
5565                 },
5566                 .replica= {
5567                         .type           = WREPL_TYPE_SGROUP,
5568                         .state          = WREPL_STATE_TOMBSTONE,
5569                         .node           = WREPL_NODE_B,
5570                         .is_static      = False,
5571                         .num_ips        = ctx->addresses_best_num,
5572                         .ips            = ctx->addresses_best,
5573                         .apply_expected = True
5574                 },
5575         },
5576         /*
5577          * sgroup,released vs. sgroup,tombstone with different ip(s)
5578          */
5579         {
5580                 .line   = __location__,
5581                 .name   = _NBT_NAME("_SR_ST_DI", 0x1C, NULL),
5582                 .wins   = {
5583                         .nb_flags       = NBT_NM_GROUP,
5584                         .mhomed         = False,
5585                         .num_ips        = ctx->addresses_best_num,
5586                         .ips            = ctx->addresses_best,
5587                         .apply_expected = True
5588                 },
5589                 .replica= {
5590                         .type           = WREPL_TYPE_SGROUP,
5591                         .state          = WREPL_STATE_TOMBSTONE,
5592                         .node           = WREPL_NODE_B,
5593                         .is_static      = False,
5594                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5595                         .ips            = addresses_B_1,
5596                         .apply_expected = True
5597                 },
5598         },
5599 /* 
5600  * special group vs. multi homed section
5601  */
5602         /*
5603          * sgroup,released vs. mhomed,active with same ip(s)
5604          */
5605         {
5606                 .line   = __location__,
5607                 .name   = _NBT_NAME("_SR_MA_SI", 0x1C, NULL),
5608                 .wins   = {
5609                         .nb_flags       = NBT_NM_GROUP,
5610                         .mhomed         = False,
5611                         .num_ips        = ctx->addresses_best_num,
5612                         .ips            = ctx->addresses_best,
5613                         .apply_expected = True
5614                 },
5615                 .replica= {
5616                         .type           = WREPL_TYPE_MHOMED,
5617                         .state          = WREPL_STATE_ACTIVE,
5618                         .node           = WREPL_NODE_B,
5619                         .is_static      = False,
5620                         .num_ips        = ctx->addresses_best_num,
5621                         .ips            = ctx->addresses_best,
5622                         .apply_expected = True
5623                 },
5624         },
5625         /*
5626          * sgroup,released vs. mhomed,active with different ip(s)
5627          */
5628         {
5629                 .line   = __location__,
5630                 .name   = _NBT_NAME("_SR_MA_DI", 0x1C, NULL),
5631                 .wins   = {
5632                         .nb_flags       = NBT_NM_GROUP,
5633                         .mhomed         = False,
5634                         .num_ips        = ctx->addresses_best_num,
5635                         .ips            = ctx->addresses_best,
5636                         .apply_expected = True
5637                 },
5638                 .replica= {
5639                         .type           = WREPL_TYPE_MHOMED,
5640                         .state          = WREPL_STATE_ACTIVE,
5641                         .node           = WREPL_NODE_B,
5642                         .is_static      = False,
5643                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5644                         .ips            = addresses_B_1,
5645                         .apply_expected = True
5646                 },
5647         },
5648         /*
5649          * sgroup,released vs. mhomed,tombstone with same ip(s)
5650          */
5651         {
5652                 .line   = __location__,
5653                 .name   = _NBT_NAME("_SR_MT_SI", 0x1C, NULL),
5654                 .wins   = {
5655                         .nb_flags       = NBT_NM_GROUP,
5656                         .mhomed         = False,
5657                         .num_ips        = ctx->addresses_best_num,
5658                         .ips            = ctx->addresses_best,
5659                         .apply_expected = True
5660                 },
5661                 .replica= {
5662                         .type           = WREPL_TYPE_MHOMED,
5663                         .state          = WREPL_STATE_TOMBSTONE,
5664                         .node           = WREPL_NODE_B,
5665                         .is_static      = False,
5666                         .num_ips        = ctx->addresses_best_num,
5667                         .ips            = ctx->addresses_best,
5668                         .apply_expected = True
5669                 },
5670         },
5671         /*
5672          * sgroup,released vs. mhomed,tombstone with different ip(s)
5673          */
5674         {
5675                 .line   = __location__,
5676                 .name   = _NBT_NAME("_SR_MT_DI", 0x1C, NULL),
5677                 .wins   = {
5678                         .nb_flags       = NBT_NM_GROUP,
5679                         .mhomed         = False,
5680                         .num_ips        = ctx->addresses_best_num,
5681                         .ips            = ctx->addresses_best,
5682                         .apply_expected = True
5683                 },
5684                 .replica= {
5685                         .type           = WREPL_TYPE_MHOMED,
5686                         .state          = WREPL_STATE_TOMBSTONE,
5687                         .node           = WREPL_NODE_B,
5688                         .is_static      = False,
5689                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5690                         .ips            = addresses_B_1,
5691                         .apply_expected = True
5692                 },
5693         },
5694 /* 
5695  * multi homed vs. unique section
5696  */
5697         /*
5698          * mhomed,released vs. unique,active with same ip(s)
5699          */
5700         {
5701                 .line   = __location__,
5702                 .name   = _NBT_NAME("_MR_UA_SI", 0x00, NULL),
5703                 .wins   = {
5704                         .nb_flags       = 0,
5705                         .mhomed         = True,
5706                         .num_ips        = ctx->addresses_best_num,
5707                         .ips            = ctx->addresses_best,
5708                         .apply_expected = True
5709                 },
5710                 .replica= {
5711                         .type           = WREPL_TYPE_UNIQUE,
5712                         .state          = WREPL_STATE_ACTIVE,
5713                         .node           = WREPL_NODE_B,
5714                         .is_static      = False,
5715                         .num_ips        = ctx->addresses_best_num,
5716                         .ips            = ctx->addresses_best,
5717                         .apply_expected = True
5718                 },
5719         },
5720         /*
5721          * mhomed,released vs. unique,active with different ip(s)
5722          */
5723         {
5724                 .line   = __location__,
5725                 .name   = _NBT_NAME("_MR_UA_DI", 0x00, NULL),
5726                 .wins   = {
5727                         .nb_flags       = 0,
5728                         .mhomed         = True,
5729                         .num_ips        = ctx->addresses_best_num,
5730                         .ips            = ctx->addresses_best,
5731                         .apply_expected = True
5732                 },
5733                 .replica= {
5734                         .type           = WREPL_TYPE_UNIQUE,
5735                         .state          = WREPL_STATE_ACTIVE,
5736                         .node           = WREPL_NODE_B,
5737                         .is_static      = False,
5738                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5739                         .ips            = addresses_B_1,
5740                         .apply_expected = True
5741                 },
5742         },
5743         /*
5744          * mhomed,released vs. unique,tombstone with same ip(s)
5745          */
5746         {
5747                 .line   = __location__,
5748                 .name   = _NBT_NAME("_MR_UT_SI", 0x00, NULL),
5749                 .wins   = {
5750                         .nb_flags       = 0,
5751                         .mhomed         = True,
5752                         .num_ips        = ctx->addresses_best_num,
5753                         .ips            = ctx->addresses_best,
5754                         .apply_expected = True
5755                 },
5756                 .replica= {
5757                         .type           = WREPL_TYPE_UNIQUE,
5758                         .state          = WREPL_STATE_TOMBSTONE,
5759                         .node           = WREPL_NODE_B,
5760                         .is_static      = False,
5761                         .num_ips        = ctx->addresses_best_num,
5762                         .ips            = ctx->addresses_best,
5763                         .apply_expected = True
5764                 },
5765         },
5766         /*
5767          * mhomed,released vs. unique,tombstone with different ip(s)
5768          */
5769         {
5770                 .line   = __location__,
5771                 .name   = _NBT_NAME("_MR_UT_DI", 0x00, NULL),
5772                 .wins   = {
5773                         .nb_flags       = 0,
5774                         .mhomed         = True,
5775                         .num_ips        = ctx->addresses_best_num,
5776                         .ips            = ctx->addresses_best,
5777                         .apply_expected = True
5778                 },
5779                 .replica= {
5780                         .type           = WREPL_TYPE_UNIQUE,
5781                         .state          = WREPL_STATE_TOMBSTONE,
5782                         .node           = WREPL_NODE_B,
5783                         .is_static      = False,
5784                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5785                         .ips            = addresses_B_1,
5786                         .apply_expected = True
5787                 },
5788         },
5789 /* 
5790  * multi homed vs. group section
5791  */
5792         /*
5793          * mhomed,released vs. group,active with same ip(s)
5794          */
5795         {
5796                 .line   = __location__,
5797                 .name   = _NBT_NAME("_MR_GA_SI", 0x00, NULL),
5798                 .wins   = {
5799                         .nb_flags       = 0,
5800                         .mhomed         = True,
5801                         .num_ips        = ctx->addresses_best_num,
5802                         .ips            = ctx->addresses_best,
5803                         .apply_expected = True
5804                 },
5805                 .replica= {
5806                         .type           = WREPL_TYPE_GROUP,
5807                         .state          = WREPL_STATE_ACTIVE,
5808                         .node           = WREPL_NODE_B,
5809                         .is_static      = False,
5810                         .num_ips        = ctx->addresses_best_num,
5811                         .ips            = ctx->addresses_best,
5812                         .apply_expected = True
5813                 },
5814         },
5815         /*
5816          * mhomed,released vs. group,active with different ip(s)
5817          */
5818         {
5819                 .line   = __location__,
5820                 .name   = _NBT_NAME("_MR_GA_DI", 0x00, NULL),
5821                 .wins   = {
5822                         .nb_flags       = 0,
5823                         .mhomed         = True,
5824                         .num_ips        = ctx->addresses_best_num,
5825                         .ips            = ctx->addresses_best,
5826                         .apply_expected = True
5827                 },
5828                 .replica= {
5829                         .type           = WREPL_TYPE_GROUP,
5830                         .state          = WREPL_STATE_ACTIVE,
5831                         .node           = WREPL_NODE_B,
5832                         .is_static      = False,
5833                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5834                         .ips            = addresses_B_1,
5835                         .apply_expected = True
5836                 },
5837         },
5838         /*
5839          * mhomed,released vs. group,tombstone with same ip(s)
5840          */
5841         {
5842                 .line   = __location__,
5843                 .name   = _NBT_NAME("_MR_GT_SI", 0x00, NULL),
5844                 .wins   = {
5845                         .nb_flags       = 0,
5846                         .mhomed         = True,
5847                         .num_ips        = ctx->addresses_best_num,
5848                         .ips            = ctx->addresses_best,
5849                         .apply_expected = True
5850                 },
5851                 .replica= {
5852                         .type           = WREPL_TYPE_GROUP,
5853                         .state          = WREPL_STATE_TOMBSTONE,
5854                         .node           = WREPL_NODE_B,
5855                         .is_static      = False,
5856                         .num_ips        = ctx->addresses_best_num,
5857                         .ips            = ctx->addresses_best,
5858                         .apply_expected = True
5859                 },
5860         },
5861         /*
5862          * mhomed,released vs. group,tombstone with different ip(s)
5863          */
5864         {
5865                 .line   = __location__,
5866                 .name   = _NBT_NAME("_MR_GT_DI", 0x00, NULL),
5867                 .wins   = {
5868                         .nb_flags       = 0,
5869                         .mhomed         = True,
5870                         .num_ips        = ctx->addresses_best_num,
5871                         .ips            = ctx->addresses_best,
5872                         .apply_expected = True
5873                 },
5874                 .replica= {
5875                         .type           = WREPL_TYPE_GROUP,
5876                         .state          = WREPL_STATE_TOMBSTONE,
5877                         .node           = WREPL_NODE_B,
5878                         .is_static      = False,
5879                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5880                         .ips            = addresses_B_1,
5881                         .apply_expected = True
5882                 },
5883         },
5884 /* 
5885  * multi homed vs. special group section
5886  */
5887         /*
5888          * mhomed,released vs. sgroup,active with same ip(s)
5889          */
5890         {
5891                 .line   = __location__,
5892                 .name   = _NBT_NAME("_MR_SA_SI", 0x00, NULL),
5893                 .wins   = {
5894                         .nb_flags       = 0,
5895                         .mhomed         = True,
5896                         .num_ips        = ctx->addresses_best_num,
5897                         .ips            = ctx->addresses_best,
5898                         .apply_expected = True
5899                 },
5900                 .replica= {
5901                         .type           = WREPL_TYPE_SGROUP,
5902                         .state          = WREPL_STATE_ACTIVE,
5903                         .node           = WREPL_NODE_B,
5904                         .is_static      = False,
5905                         .num_ips        = ctx->addresses_best_num,
5906                         .ips            = ctx->addresses_best,
5907                         .apply_expected = True
5908                 },
5909         },
5910         /*
5911          * mhomed,released vs. sgroup,active with different ip(s)
5912          */
5913         {
5914                 .line   = __location__,
5915                 .name   = _NBT_NAME("_MR_SA_DI", 0x00, NULL),
5916                 .wins   = {
5917                         .nb_flags       = 0,
5918                         .mhomed         = True,
5919                         .num_ips        = ctx->addresses_best_num,
5920                         .ips            = ctx->addresses_best,
5921                         .apply_expected = True
5922                 },
5923                 .replica= {
5924                         .type           = WREPL_TYPE_SGROUP,
5925                         .state          = WREPL_STATE_ACTIVE,
5926                         .node           = WREPL_NODE_B,
5927                         .is_static      = False,
5928                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5929                         .ips            = addresses_B_1,
5930                         .apply_expected = True
5931                 },
5932         },
5933         /*
5934          * mhomed,released vs. sgroup,tombstone with same ip(s)
5935          */
5936         {
5937                 .line   = __location__,
5938                 .name   = _NBT_NAME("_MR_ST_SI", 0x00, NULL),
5939                 .wins   = {
5940                         .nb_flags       = 0,
5941                         .mhomed         = True,
5942                         .num_ips        = ctx->addresses_best_num,
5943                         .ips            = ctx->addresses_best,
5944                         .apply_expected = True
5945                 },
5946                 .replica= {
5947                         .type           = WREPL_TYPE_SGROUP,
5948                         .state          = WREPL_STATE_TOMBSTONE,
5949                         .node           = WREPL_NODE_B,
5950                         .is_static      = False,
5951                         .num_ips        = ctx->addresses_best_num,
5952                         .ips            = ctx->addresses_best,
5953                         .apply_expected = True
5954                 },
5955         },
5956         /*
5957          * mhomed,released vs. sgroup,tombstone with different ip(s)
5958          */
5959         {
5960                 .line   = __location__,
5961                 .name   = _NBT_NAME("_MR_ST_DI", 0x00, NULL),
5962                 .wins   = {
5963                         .nb_flags       = 0,
5964                         .mhomed         = True,
5965                         .num_ips        = ctx->addresses_best_num,
5966                         .ips            = ctx->addresses_best,
5967                         .apply_expected = True
5968                 },
5969                 .replica= {
5970                         .type           = WREPL_TYPE_SGROUP,
5971                         .state          = WREPL_STATE_TOMBSTONE,
5972                         .node           = WREPL_NODE_B,
5973                         .is_static      = False,
5974                         .num_ips        = ARRAY_SIZE(addresses_B_1),
5975                         .ips            = addresses_B_1,
5976                         .apply_expected = True
5977                 },
5978         },
5979 /* 
5980  * multi homed vs. multi homed section
5981  */
5982         /*
5983          * mhomed,released vs. mhomed,active with same ip(s)
5984          */
5985         {
5986                 .line   = __location__,
5987                 .name   = _NBT_NAME("_MR_MA_SI", 0x00, NULL),
5988                 .wins   = {
5989                         .nb_flags       = 0,
5990                         .mhomed         = True,
5991                         .num_ips        = ctx->addresses_best_num,
5992                         .ips            = ctx->addresses_best,
5993                         .apply_expected = True
5994                 },
5995                 .replica= {
5996                         .type           = WREPL_TYPE_MHOMED,
5997                         .state          = WREPL_STATE_ACTIVE,
5998                         .node           = WREPL_NODE_B,
5999                         .is_static      = False,
6000                         .num_ips        = ctx->addresses_best_num,
6001                         .ips            = ctx->addresses_best,
6002                         .apply_expected = True
6003                 },
6004         },
6005         /*
6006          * mhomed,released vs. mhomed,active with different ip(s)
6007          */
6008         {
6009                 .line   = __location__,
6010                 .name   = _NBT_NAME("_MR_MA_DI", 0x00, NULL),
6011                 .wins   = {
6012                         .nb_flags       = 0,
6013                         .mhomed         = True,
6014                         .num_ips        = ctx->addresses_best_num,
6015                         .ips            = ctx->addresses_best,
6016                         .apply_expected = True
6017                 },
6018                 .replica= {
6019                         .type           = WREPL_TYPE_MHOMED,
6020                         .state          = WREPL_STATE_ACTIVE,
6021                         .node           = WREPL_NODE_B,
6022                         .is_static      = False,
6023                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6024                         .ips            = addresses_B_1,
6025                         .apply_expected = True
6026                 },
6027         },
6028         /*
6029          * mhomed,released vs. mhomed,tombstone with same ip(s)
6030          */
6031         {
6032                 .line   = __location__,
6033                 .name   = _NBT_NAME("_MR_MT_SI", 0x00, NULL),
6034                 .wins   = {
6035                         .nb_flags       = 0,
6036                         .mhomed         = True,
6037                         .num_ips        = ctx->addresses_best_num,
6038                         .ips            = ctx->addresses_best,
6039                         .apply_expected = True
6040                 },
6041                 .replica= {
6042                         .type           = WREPL_TYPE_MHOMED,
6043                         .state          = WREPL_STATE_TOMBSTONE,
6044                         .node           = WREPL_NODE_B,
6045                         .is_static      = False,
6046                         .num_ips        = ctx->addresses_best_num,
6047                         .ips            = ctx->addresses_best,
6048                         .apply_expected = True
6049                 },
6050         },
6051         /*
6052          * mhomed,released vs. mhomed,tombstone with different ip(s)
6053          */
6054         {
6055                 .line   = __location__,
6056                 .name   = _NBT_NAME("_MR_MT_DI", 0x00, NULL),
6057                 .wins   = {
6058                         .nb_flags       = 0,
6059                         .mhomed         = True,
6060                         .num_ips        = ctx->addresses_best_num,
6061                         .ips            = ctx->addresses_best,
6062                         .apply_expected = True
6063                 },
6064                 .replica= {
6065                         .type           = WREPL_TYPE_MHOMED,
6066                         .state          = WREPL_STATE_TOMBSTONE,
6067                         .node           = WREPL_NODE_B,
6068                         .is_static      = False,
6069                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6070                         .ips            = addresses_B_1,
6071                         .apply_expected = True
6072                 },
6073         },
6074         };
6075
6076         if (!ctx) return False;
6077
6078         printf("Test Replica records vs. owned released records\n");
6079
6080         for(i=0; ret && i < ARRAY_SIZE(records); i++) {
6081                 printf("%s => %s\n", nbt_name_string(ctx, &records[i].name),
6082                         (records[i].replica.apply_expected?"REPLACE":"NOT REPLACE"));
6083
6084                 /*
6085                  * Setup Register
6086                  */
6087                 name_register->in.name          = records[i].name;
6088                 name_register->in.dest_addr     = ctx->address;
6089                 name_register->in.address       = records[i].wins.ips[0].ip;
6090                 name_register->in.nb_flags      = records[i].wins.nb_flags;
6091                 name_register->in.register_demand= False;
6092                 name_register->in.broadcast     = False;
6093                 name_register->in.multi_homed   = records[i].wins.mhomed;
6094                 name_register->in.ttl           = 300000;
6095                 name_register->in.timeout       = 70;
6096                 name_register->in.retries       = 0;
6097
6098                 status = nbt_name_register(ctx->nbtsock, ctx, name_register);
6099                 if (NT_STATUS_EQUAL(status, NT_STATUS_IO_TIMEOUT)) {
6100                         printf("No response from %s for name register\n", ctx->address);
6101                         ret = False;
6102                 }
6103                 if (!NT_STATUS_IS_OK(status)) {
6104                         printf("Bad response from %s for name register - %s\n",
6105                                ctx->address, nt_errstr(status));
6106                         ret = False;
6107                 }
6108                 CHECK_VALUE(name_register->out.rcode, 0);
6109                 CHECK_VALUE_STRING(name_register->out.reply_from, ctx->address);
6110                 CHECK_VALUE(name_register->out.name.type, records[i].name.type);
6111                 CHECK_VALUE_STRING(name_register->out.name.name, records[i].name.name);
6112                 CHECK_VALUE_STRING(name_register->out.name.scope, records[i].name.scope);
6113                 CHECK_VALUE_STRING(name_register->out.reply_addr, records[i].wins.ips[0].ip);
6114
6115                 /* release the record */
6116                 release->in.name        = records[i].name;
6117                 release->in.dest_addr   = ctx->address;
6118                 release->in.address     = records[i].wins.ips[0].ip;
6119                 release->in.nb_flags    = records[i].wins.nb_flags;
6120                 release->in.broadcast   = False;
6121                 release->in.timeout     = 30;
6122                 release->in.retries     = 0;
6123
6124                 status = nbt_name_release(ctx->nbtsock, ctx, release);
6125                 if (NT_STATUS_EQUAL(status, NT_STATUS_IO_TIMEOUT)) {
6126                         printf("No response from %s for name release\n", ctx->address);
6127                         return False;
6128                 }
6129                 if (!NT_STATUS_IS_OK(status)) {
6130                         printf("Bad response from %s for name query - %s\n",
6131                                ctx->address, nt_errstr(status));
6132                         return False;
6133                 }
6134                 CHECK_VALUE(release->out.rcode, 0);
6135
6136                 /*
6137                  * Setup Replica
6138                  */
6139                 wins_name->name         = &records[i].name;
6140                 wins_name->flags        = WREPL_NAME_FLAGS(records[i].replica.type,
6141                                                            records[i].replica.state,
6142                                                            records[i].replica.node,
6143                                                            records[i].replica.is_static);
6144                 wins_name->id           = ++ctx->b.max_version;
6145                 if (wins_name->flags & 2) {
6146                         wins_name->addresses.addresses.num_ips = records[i].replica.num_ips;
6147                         wins_name->addresses.addresses.ips     = discard_const(records[i].replica.ips);
6148                 } else {
6149                         wins_name->addresses.ip = records[i].replica.ips[0].ip;
6150                 }
6151                 wins_name->unknown      = "255.255.255.255";
6152
6153                 ret &= test_wrepl_update_one(ctx, &ctx->b, wins_name);
6154                 ret &= test_wrepl_is_applied(ctx, &ctx->b, wins_name,
6155                                              records[i].replica.apply_expected);
6156
6157                 if (records[i].replica.apply_expected) {
6158                         wins_name->name         = &records[i].name;
6159                         wins_name->flags        = WREPL_NAME_FLAGS(WREPL_TYPE_UNIQUE,
6160                                                                    WREPL_STATE_TOMBSTONE,
6161                                                                    WREPL_NODE_B, False);
6162                         wins_name->id           = ++ctx->b.max_version;
6163                         wins_name->addresses.ip = addresses_B_1[0].ip;
6164                         wins_name->unknown      = "255.255.255.255";
6165
6166                         ret &= test_wrepl_update_one(ctx, &ctx->b, wins_name);
6167                         ret &= test_wrepl_is_applied(ctx, &ctx->b, wins_name, True);
6168                 } else {
6169                         release->in.name        = records[i].name;
6170                         release->in.dest_addr   = ctx->address;
6171                         release->in.address     = records[i].wins.ips[0].ip;
6172                         release->in.nb_flags    = records[i].wins.nb_flags;
6173                         release->in.broadcast   = False;
6174                         release->in.timeout     = 30;
6175                         release->in.retries     = 0;
6176
6177                         status = nbt_name_release(ctx->nbtsock, ctx, release);
6178                         if (NT_STATUS_EQUAL(status, NT_STATUS_IO_TIMEOUT)) {
6179                                 printf("No response from %s for name release\n", ctx->address);
6180                                 return False;
6181                         }
6182                         if (!NT_STATUS_IS_OK(status)) {
6183                                 printf("Bad response from %s for name query - %s\n",
6184                                        ctx->address, nt_errstr(status));
6185                                 return False;
6186                         }
6187                         CHECK_VALUE(release->out.rcode, 0);
6188                 }
6189 done:
6190                 if (!ret) {
6191                         printf("conflict handled wrong or record[%u]: %s\n", i, records[i].line);
6192                         return ret;
6193                 }
6194         }
6195
6196         return ret;
6197 }
6198
6199 struct test_conflict_owned_active_vs_replica_struct {
6200         const char *line; /* just better debugging */
6201         const char *section; /* just better debugging */
6202         struct nbt_name name;
6203         BOOL skip;
6204         struct {
6205                 uint32_t nb_flags;
6206                 BOOL mhomed;
6207                 uint32_t num_ips;
6208                 const struct wrepl_ip *ips;
6209                 BOOL apply_expected;
6210         } wins;
6211         struct {
6212                 uint32_t timeout;
6213                 BOOL positive;
6214                 BOOL expect_release;
6215                 BOOL late_release;
6216                 BOOL ret;
6217                 /* when num_ips == 0, then .wins.ips are used */
6218                 uint32_t num_ips;
6219                 const struct wrepl_ip *ips;
6220         } defend;
6221         struct {
6222                 enum wrepl_name_type type;
6223                 enum wrepl_name_state state;
6224                 enum wrepl_name_node node;
6225                 BOOL is_static;
6226                 uint32_t num_ips;
6227                 const struct wrepl_ip *ips;
6228                 BOOL apply_expected;
6229                 BOOL mhomed_merge;
6230                 BOOL sgroup_merge;
6231         } replica;
6232 };
6233
6234 static void test_conflict_owned_active_vs_replica_handler(struct nbt_name_socket *nbtsock, 
6235                                                           struct nbt_name_packet *req_packet, 
6236                                                           const struct nbt_peer_socket *src);
6237
6238 static BOOL test_conflict_owned_active_vs_replica(struct test_wrepl_conflict_conn *ctx)
6239 {
6240         BOOL ret = True;
6241         NTSTATUS status;
6242         struct wrepl_wins_name wins_name_;
6243         struct wrepl_wins_name *wins_name = &wins_name_;
6244         struct nbt_name_register name_register_;
6245         struct nbt_name_register *name_register = &name_register_;
6246         struct nbt_name_release release_;
6247         struct nbt_name_release *release = &release_;
6248         uint32_t i;
6249         struct test_conflict_owned_active_vs_replica_struct records[] = {
6250 /* 
6251  * unique vs. unique section
6252  */
6253         /*
6254          * unique,active vs. unique,active with same ip(s), unchecked
6255          */
6256         {
6257                 .line   = __location__,
6258                 .name   = _NBT_NAME("_UA_UA_SI_U", 0x00, NULL),
6259                 .wins   = {
6260                         .nb_flags       = 0,
6261                         .mhomed         = False,
6262                         .num_ips        = ctx->addresses_best_num,
6263                         .ips            = ctx->addresses_best,
6264                         .apply_expected = True
6265                 },
6266                 .defend = {
6267                         .timeout        = 0,
6268                 },
6269                 .replica= {
6270                         .type           = WREPL_TYPE_UNIQUE,
6271                         .state          = WREPL_STATE_ACTIVE,
6272                         .node           = WREPL_NODE_B,
6273                         .is_static      = False,
6274                         .num_ips        = ctx->addresses_best_num,
6275                         .ips            = ctx->addresses_best,
6276                         .apply_expected = True
6277                 },
6278         },
6279         /*
6280          * unique,active vs. unique,active with different ip(s), positive response
6281          */
6282         {
6283                 .line   = __location__,
6284                 .name   = _NBT_NAME("_UA_UA_DI_P", 0x00, NULL),
6285                 .wins   = {
6286                         .nb_flags       = 0,
6287                         .mhomed         = False,
6288                         .num_ips        = ctx->addresses_best_num,
6289                         .ips            = ctx->addresses_best,
6290                         .apply_expected = True
6291                 },
6292                 .defend = {
6293                         .timeout        = 10,
6294                         .positive       = True,
6295                 },
6296                 .replica= {
6297                         .type           = WREPL_TYPE_UNIQUE,
6298                         .state          = WREPL_STATE_ACTIVE,
6299                         .node           = WREPL_NODE_B,
6300                         .is_static      = False,
6301                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6302                         .ips            = addresses_B_1,
6303                         .apply_expected = False
6304                 },
6305         },
6306         /*
6307          * unique,active vs. unique,active with different ip(s), positive response other ips
6308          */
6309         {
6310                 .line   = __location__,
6311                 .name   = _NBT_NAME("_UA_UA_DI_O", 0x00, NULL),
6312                 .wins   = {
6313                         .nb_flags       = 0,
6314                         .mhomed         = False,
6315                         .num_ips        = ctx->addresses_best_num,
6316                         .ips            = ctx->addresses_best,
6317                         .apply_expected = True
6318                 },
6319                 .defend = {
6320                         .timeout        = 10,
6321                         .positive       = True,
6322                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
6323                         .ips            = addresses_A_3_4,
6324                 },
6325                 .replica= {
6326                         .type           = WREPL_TYPE_UNIQUE,
6327                         .state          = WREPL_STATE_ACTIVE,
6328                         .node           = WREPL_NODE_B,
6329                         .is_static      = False,
6330                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6331                         .ips            = addresses_B_1,
6332                         .apply_expected = False
6333                 },
6334         },
6335         /*
6336          * unique,active vs. unique,active with different ip(s), negative response
6337          */
6338         {
6339                 .line   = __location__,
6340                 .name   = _NBT_NAME("_UA_UA_DI_N", 0x00, NULL),
6341                 .wins   = {
6342                         .nb_flags       = 0,
6343                         .mhomed         = False,
6344                         .num_ips        = ctx->addresses_best_num,
6345                         .ips            = ctx->addresses_best,
6346                         .apply_expected = True
6347                 },
6348                 .defend = {
6349                         .timeout        = 10,
6350                         .positive       = False,
6351                 },
6352                 .replica= {
6353                         .type           = WREPL_TYPE_UNIQUE,
6354                         .state          = WREPL_STATE_ACTIVE,
6355                         .node           = WREPL_NODE_B,
6356                         .is_static      = False,
6357                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6358                         .ips            = addresses_B_1,
6359                         .apply_expected = True
6360                 },
6361         },
6362         /*
6363          * unique,active vs. unique,tombstone with same ip(s), unchecked
6364          */
6365         {
6366                 .line   = __location__,
6367                 .name   = _NBT_NAME("_UA_UT_SI_U", 0x00, NULL),
6368                 .wins   = {
6369                         .nb_flags       = 0,
6370                         .mhomed         = False,
6371                         .num_ips        = ctx->addresses_best_num,
6372                         .ips            = ctx->addresses_best,
6373                         .apply_expected = True
6374                 },
6375                 .defend = {
6376                         .timeout        = 0,
6377                 },
6378                 .replica= {
6379                         .type           = WREPL_TYPE_UNIQUE,
6380                         .state          = WREPL_STATE_TOMBSTONE,
6381                         .node           = WREPL_NODE_B,
6382                         .is_static      = False,
6383                         .num_ips        = ctx->addresses_best_num,
6384                         .ips            = ctx->addresses_best,
6385                         .apply_expected = False
6386                 },
6387         },
6388         /*
6389          * unique,active vs. unique,tombstone with different ip(s), unchecked
6390          */
6391         {
6392                 .line   = __location__,
6393                 .name   = _NBT_NAME("_UA_UT_DI_U", 0x00, NULL),
6394                 .wins   = {
6395                         .nb_flags       = 0,
6396                         .mhomed         = False,
6397                         .num_ips        = ctx->addresses_best_num,
6398                         .ips            = ctx->addresses_best,
6399                         .apply_expected = True
6400                 },
6401                 .defend = {
6402                         .timeout        = 0,
6403                 },
6404                 .replica= {
6405                         .type           = WREPL_TYPE_UNIQUE,
6406                         .state          = WREPL_STATE_TOMBSTONE,
6407                         .node           = WREPL_NODE_B,
6408                         .is_static      = False,
6409                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6410                         .ips            = addresses_B_1,
6411                         .apply_expected = False
6412                 },
6413         },
6414 /* 
6415  * unique vs. group section
6416  */
6417         /*
6418          * unique,active vs. group,active with same ip(s), release expected
6419          */
6420         {
6421                 .line   = __location__,
6422                 .name   = _NBT_NAME("_UA_GA_SI_R", 0x00, NULL),
6423                 .wins   = {
6424                         .nb_flags       = 0,
6425                         .mhomed         = False,
6426                         .num_ips        = ctx->addresses_best_num,
6427                         .ips            = ctx->addresses_best,
6428                         .apply_expected = True
6429                 },
6430                 .defend = {
6431                         .timeout        = 10,
6432                         .expect_release = True,
6433                 },
6434                 .replica= {
6435                         .type           = WREPL_TYPE_GROUP,
6436                         .state          = WREPL_STATE_ACTIVE,
6437                         .node           = WREPL_NODE_B,
6438                         .is_static      = False,
6439                         .num_ips        = ctx->addresses_best_num,
6440                         .ips            = ctx->addresses_best,
6441                         .apply_expected = True
6442                 },
6443         },
6444         /*
6445          * unique,active vs. group,active with different ip(s), release expected
6446          */
6447         {
6448                 .line   = __location__,
6449                 .name   = _NBT_NAME("_UA_GA_DI_R", 0x00, NULL),
6450                 .wins   = {
6451                         .nb_flags       = 0,
6452                         .mhomed         = False,
6453                         .num_ips        = ctx->addresses_best_num,
6454                         .ips            = ctx->addresses_best,
6455                         .apply_expected = True
6456                 },
6457                 .defend = {
6458                         .timeout        = 10,
6459                         .expect_release = True,
6460                 },
6461                 .replica= {
6462                         .type           = WREPL_TYPE_GROUP,
6463                         .state          = WREPL_STATE_ACTIVE,
6464                         .node           = WREPL_NODE_B,
6465                         .is_static      = False,
6466                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6467                         .ips            = addresses_B_1,
6468                         .apply_expected = True
6469                 },
6470         },
6471         /*
6472          * unique,active vs. group,tombstone with same ip(s), unchecked
6473          */
6474         {
6475                 .line   = __location__,
6476                 .name   = _NBT_NAME("_UA_GT_SI_U", 0x00, NULL),
6477                 .wins   = {
6478                         .nb_flags       = 0,
6479                         .mhomed         = False,
6480                         .num_ips        = ctx->addresses_best_num,
6481                         .ips            = ctx->addresses_best,
6482                         .apply_expected = True
6483                 },
6484                 .defend = {
6485                         .timeout        = 0,
6486                 },
6487                 .replica= {
6488                         .type           = WREPL_TYPE_GROUP,
6489                         .state          = WREPL_STATE_TOMBSTONE,
6490                         .node           = WREPL_NODE_B,
6491                         .is_static      = False,
6492                         .num_ips        = ctx->addresses_best_num,
6493                         .ips            = ctx->addresses_best,
6494                         .apply_expected = False
6495                 },
6496         },
6497         /*
6498          * unique,active vs. group,tombstone with different ip(s), unchecked
6499          */
6500         {
6501                 .line   = __location__,
6502                 .name   = _NBT_NAME("_UA_GT_DI_U", 0x00, NULL),
6503                 .wins   = {
6504                         .nb_flags       = 0,
6505                         .mhomed         = False,
6506                         .num_ips        = ctx->addresses_best_num,
6507                         .ips            = ctx->addresses_best,
6508                         .apply_expected = True
6509                 },
6510                 .defend = {
6511                         .timeout        = 0,
6512                 },
6513                 .replica= {
6514                         .type           = WREPL_TYPE_GROUP,
6515                         .state          = WREPL_STATE_TOMBSTONE,
6516                         .node           = WREPL_NODE_B,
6517                         .is_static      = False,
6518                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6519                         .ips            = addresses_B_1,
6520                         .apply_expected = False
6521                 },
6522         },
6523 /* 
6524  * unique vs. special group section
6525  */
6526         /*
6527          * unique,active vs. sgroup,active with same ip(s), release expected
6528          */
6529         {
6530                 .line   = __location__,
6531                 .name   = _NBT_NAME("_UA_SA_SI_R", 0x00, NULL),
6532                 .wins   = {
6533                         .nb_flags       = 0,
6534                         .mhomed         = False,
6535                         .num_ips        = ctx->addresses_best_num,
6536                         .ips            = ctx->addresses_best,
6537                         .apply_expected = True
6538                 },
6539                 .defend = {
6540                         .timeout        = 10,
6541                         .expect_release = True,
6542                 },
6543                 .replica= {
6544                         .type           = WREPL_TYPE_SGROUP,
6545                         .state          = WREPL_STATE_ACTIVE,
6546                         .node           = WREPL_NODE_B,
6547                         .is_static      = False,
6548                         .num_ips        = ctx->addresses_best_num,
6549                         .ips            = ctx->addresses_best,
6550                         .apply_expected = True
6551                 },
6552         },
6553         /*
6554          * unique,active vs. group,active with different ip(s), release expected
6555          */
6556         {
6557                 .line   = __location__,
6558                 .name   = _NBT_NAME("_UA_SA_DI_R", 0x00, NULL),
6559                 .wins   = {
6560                         .nb_flags       = 0,
6561                         .mhomed         = False,
6562                         .num_ips        = ctx->addresses_best_num,
6563                         .ips            = ctx->addresses_best,
6564                         .apply_expected = True
6565                 },
6566                 .defend = {
6567                         .timeout        = 10,
6568                         .expect_release = True,
6569                 },
6570                 .replica= {
6571                         .type           = WREPL_TYPE_SGROUP,
6572                         .state          = WREPL_STATE_ACTIVE,
6573                         .node           = WREPL_NODE_B,
6574                         .is_static      = False,
6575                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6576                         .ips            = addresses_B_1,
6577                         .apply_expected = True
6578                 },
6579         },
6580         /*
6581          * unique,active vs. sgroup,tombstone with same ip(s), unchecked
6582          */
6583         {
6584                 .line   = __location__,
6585                 .name   = _NBT_NAME("_UA_ST_SI_U", 0x00, NULL),
6586                 .wins   = {
6587                         .nb_flags       = 0,
6588                         .mhomed         = False,
6589                         .num_ips        = ctx->addresses_best_num,
6590                         .ips            = ctx->addresses_best,
6591                         .apply_expected = True
6592                 },
6593                 .defend = {
6594                         .timeout        = 0,
6595                 },
6596                 .replica= {
6597                         .type           = WREPL_TYPE_SGROUP,
6598                         .state          = WREPL_STATE_TOMBSTONE,
6599                         .node           = WREPL_NODE_B,
6600                         .is_static      = False,
6601                         .num_ips        = ctx->addresses_best_num,
6602                         .ips            = ctx->addresses_best,
6603                         .apply_expected = False
6604                 },
6605         },
6606         /*
6607          * unique,active vs. sgroup,tombstone with different ip(s), unchecked
6608          */
6609         {
6610                 .line   = __location__,
6611                 .name   = _NBT_NAME("_UA_ST_DI_U", 0x00, NULL),
6612                 .wins   = {
6613                         .nb_flags       = 0,
6614                         .mhomed         = False,
6615                         .num_ips        = ctx->addresses_best_num,
6616                         .ips            = ctx->addresses_best,
6617                         .apply_expected = True
6618                 },
6619                 .defend = {
6620                         .timeout        = 0,
6621                 },
6622                 .replica= {
6623                         .type           = WREPL_TYPE_SGROUP,
6624                         .state          = WREPL_STATE_TOMBSTONE,
6625                         .node           = WREPL_NODE_B,
6626                         .is_static      = False,
6627                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6628                         .ips            = addresses_B_1,
6629                         .apply_expected = False
6630                 },
6631         },
6632 /* 
6633  * unique vs. multi homed section
6634  */
6635         /*
6636          * unique,active vs. mhomed,active with same ip(s), unchecked
6637          */
6638         {
6639                 .line   = __location__,
6640                 .name   = _NBT_NAME("_UA_MA_SI_U", 0x00, NULL),
6641                 .wins   = {
6642                         .nb_flags       = 0,
6643                         .mhomed         = False,
6644                         .num_ips        = ctx->addresses_best_num,
6645                         .ips            = ctx->addresses_best,
6646                         .apply_expected = True
6647                 },
6648                 .defend = {
6649                         .timeout        = 0,
6650                 },
6651                 .replica= {
6652                         .type           = WREPL_TYPE_MHOMED,
6653                         .state          = WREPL_STATE_ACTIVE,
6654                         .node           = WREPL_NODE_B,
6655                         .is_static      = False,
6656                         .num_ips        = ctx->addresses_best_num,
6657                         .ips            = ctx->addresses_best,
6658                         .apply_expected = True
6659                 },
6660         },
6661         /*
6662          * unique,active vs. mhomed,active with superset ip(s), unchecked
6663          */
6664         {
6665                 .line   = __location__,
6666                 .name   = _NBT_NAME("_UA_MA_SP_U", 0x00, NULL),
6667                 .wins   = {
6668                         .nb_flags       = 0,
6669                         .mhomed         = False,
6670                         .num_ips        = ctx->addresses_best_num,
6671                         .ips            = ctx->addresses_best,
6672                         .apply_expected = True
6673                 },
6674                 .defend = {
6675                         .timeout        = 0,
6676                 },
6677                 .replica= {
6678                         .type           = WREPL_TYPE_MHOMED,
6679                         .state          = WREPL_STATE_ACTIVE,
6680                         .node           = WREPL_NODE_B,
6681                         .is_static      = False,
6682                         .num_ips        = ctx->addresses_all_num,
6683                         .ips            = ctx->addresses_all,
6684                         .apply_expected = True
6685                 },
6686         },
6687         /*
6688          * unique,active vs. mhomed,active with different ip(s), positive response
6689          */
6690         {
6691                 .line   = __location__,
6692                 .name   = _NBT_NAME("_UA_MA_DI_P", 0x00, NULL),
6693                 .wins   = {
6694                         .nb_flags       = 0,
6695                         .mhomed         = False,
6696                         .num_ips        = ctx->addresses_best_num,
6697                         .ips            = ctx->addresses_best,
6698                         .apply_expected = True
6699                 },
6700                 .defend = {
6701                         .timeout        = 10,
6702                         .positive       = True,
6703                 },
6704                 .replica= {
6705                         .type           = WREPL_TYPE_MHOMED,
6706                         .state          = WREPL_STATE_ACTIVE,
6707                         .node           = WREPL_NODE_B,
6708                         .is_static      = False,
6709                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
6710                         .ips            = addresses_B_3_4,
6711                         .apply_expected = False
6712                 },
6713         },
6714         /*
6715          * unique,active vs. mhomed,active with different ip(s), positive response other ips
6716          */
6717         {
6718                 .line   = __location__,
6719                 .name   = _NBT_NAME("_UA_MA_DI_O", 0x00, NULL),
6720                 .wins   = {
6721                         .nb_flags       = 0,
6722                         .mhomed         = False,
6723                         .num_ips        = ctx->addresses_best_num,
6724                         .ips            = ctx->addresses_best,
6725                         .apply_expected = True
6726                 },
6727                 .defend = {
6728                         .timeout        = 10,
6729                         .positive       = True,
6730                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
6731                         .ips            = addresses_A_3_4,
6732                 },
6733                 .replica= {
6734                         .type           = WREPL_TYPE_MHOMED,
6735                         .state          = WREPL_STATE_ACTIVE,
6736                         .node           = WREPL_NODE_B,
6737                         .is_static      = False,
6738                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
6739                         .ips            = addresses_B_3_4,
6740                         .apply_expected = False
6741                 },
6742         },
6743         /*
6744          * unique,active vs. mhomed,active with different ip(s), negative response
6745          */
6746         {
6747                 .line   = __location__,
6748                 .name   = _NBT_NAME("_UA_MA_DI_N", 0x00, NULL),
6749                 .wins   = {
6750                         .nb_flags       = 0,
6751                         .mhomed         = False,
6752                         .num_ips        = ctx->addresses_best_num,
6753                         .ips            = ctx->addresses_best,
6754                         .apply_expected = True
6755                 },
6756                 .defend = {
6757                         .timeout        = 10,
6758                         .positive       = False,
6759                 },
6760                 .replica= {
6761                         .type           = WREPL_TYPE_MHOMED,
6762                         .state          = WREPL_STATE_ACTIVE,
6763                         .node           = WREPL_NODE_B,
6764                         .is_static      = False,
6765                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
6766                         .ips            = addresses_B_3_4,
6767                         .apply_expected = True
6768                 },
6769         },
6770         /*
6771          * unique,active vs. mhomed,tombstone with same ip(s), unchecked
6772          */
6773         {
6774                 .line   = __location__,
6775                 .name   = _NBT_NAME("_UA_MT_SI_U", 0x00, NULL),
6776                 .wins   = {
6777                         .nb_flags       = 0,
6778                         .mhomed         = False,
6779                         .num_ips        = ctx->addresses_best_num,
6780                         .ips            = ctx->addresses_best,
6781                         .apply_expected = True
6782                 },
6783                 .defend = {
6784                         .timeout        = 0,
6785                 },
6786                 .replica= {
6787                         .type           = WREPL_TYPE_MHOMED,
6788                         .state          = WREPL_STATE_TOMBSTONE,
6789                         .node           = WREPL_NODE_B,
6790                         .is_static      = False,
6791                         .num_ips        = ctx->addresses_best_num,
6792                         .ips            = ctx->addresses_best,
6793                         .apply_expected = False
6794                 },
6795         },
6796         /*
6797          * unique,active vs. mhomed,tombstone with different ip(s), unchecked
6798          */
6799         {
6800                 .line   = __location__,
6801                 .name   = _NBT_NAME("_UA_MT_DI_U", 0x00, NULL),
6802                 .wins   = {
6803                         .nb_flags       = 0,
6804                         .mhomed         = False,
6805                         .num_ips        = ctx->addresses_best_num,
6806                         .ips            = ctx->addresses_best,
6807                         .apply_expected = True
6808                 },
6809                 .defend = {
6810                         .timeout        = 0,
6811                 },
6812                 .replica= {
6813                         .type           = WREPL_TYPE_MHOMED,
6814                         .state          = WREPL_STATE_TOMBSTONE,
6815                         .node           = WREPL_NODE_B,
6816                         .is_static      = False,
6817                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
6818                         .ips            = addresses_B_3_4,
6819                         .apply_expected = False
6820                 },
6821         },
6822 /* 
6823  * normal group vs. unique section
6824  */
6825         /*
6826          * group,active vs. unique,active with same ip(s), unchecked
6827          */
6828         {
6829                 .line   = __location__,
6830                 .name   = _NBT_NAME("_GA_UA_SI_U", 0x00, NULL),
6831                 .wins   = {
6832                         .nb_flags       = NBT_NM_GROUP,
6833                         .mhomed         = False,
6834                         .num_ips        = ctx->addresses_best_num,
6835                         .ips            = ctx->addresses_best,
6836                         .apply_expected = True
6837                 },
6838                 .defend = {
6839                         .timeout        = 0,
6840                 },
6841                 .replica= {
6842                         .type           = WREPL_TYPE_UNIQUE,
6843                         .state          = WREPL_STATE_ACTIVE,
6844                         .node           = WREPL_NODE_B,
6845                         .is_static      = False,
6846                         .num_ips        = ctx->addresses_best_num,
6847                         .ips            = ctx->addresses_best,
6848                         .apply_expected = False
6849                 },
6850         },
6851         /*
6852          * group,active vs. unique,active with different ip(s), unchecked
6853          */
6854         {
6855                 .line   = __location__,
6856                 .name   = _NBT_NAME("_GA_UA_DI_U", 0x00, NULL),
6857                 .wins   = {
6858                         .nb_flags       = NBT_NM_GROUP,
6859                         .mhomed         = False,
6860                         .num_ips        = ctx->addresses_best_num,
6861                         .ips            = ctx->addresses_best,
6862                         .apply_expected = True
6863                 },
6864                 .defend = {
6865                         .timeout        = 0,
6866                 },
6867                 .replica= {
6868                         .type           = WREPL_TYPE_UNIQUE,
6869                         .state          = WREPL_STATE_ACTIVE,
6870                         .node           = WREPL_NODE_B,
6871                         .is_static      = False,
6872                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6873                         .ips            = addresses_B_1,
6874                         .apply_expected = False
6875                 },
6876         },
6877         /*
6878          * group,active vs. unique,tombstone with same ip(s), unchecked
6879          */
6880         {
6881                 .line   = __location__,
6882                 .name   = _NBT_NAME("_GA_UT_SI_U", 0x00, NULL),
6883                 .wins   = {
6884                         .nb_flags       = NBT_NM_GROUP,
6885                         .mhomed         = False,
6886                         .num_ips        = ctx->addresses_best_num,
6887                         .ips            = ctx->addresses_best,
6888                         .apply_expected = True
6889                 },
6890                 .defend = {
6891                         .timeout        = 0,
6892                 },
6893                 .replica= {
6894                         .type           = WREPL_TYPE_UNIQUE,
6895                         .state          = WREPL_STATE_TOMBSTONE,
6896                         .node           = WREPL_NODE_B,
6897                         .is_static      = False,
6898                         .num_ips        = ctx->addresses_best_num,
6899                         .ips            = ctx->addresses_best,
6900                         .apply_expected = False
6901                 },
6902         },
6903         /*
6904          * group,active vs. unique,tombstone with different ip(s), unchecked
6905          */
6906         {
6907                 .line   = __location__,
6908                 .name   = _NBT_NAME("_GA_UT_DI_U", 0x00, NULL),
6909                 .wins   = {
6910                         .nb_flags       = NBT_NM_GROUP,
6911                         .mhomed         = False,
6912                         .num_ips        = ctx->addresses_best_num,
6913                         .ips            = ctx->addresses_best,
6914                         .apply_expected = True
6915                 },
6916                 .defend = {
6917                         .timeout        = 0,
6918                 },
6919                 .replica= {
6920                         .type           = WREPL_TYPE_UNIQUE,
6921                         .state          = WREPL_STATE_TOMBSTONE,
6922                         .node           = WREPL_NODE_B,
6923                         .is_static      = False,
6924                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6925                         .ips            = addresses_B_1,
6926                         .apply_expected = False
6927                 },
6928         },
6929 /* 
6930  * normal group vs. normal group section
6931  */
6932         /*
6933          * group,active vs. group,active with same ip(s), unchecked
6934          */
6935         {
6936                 .line   = __location__,
6937                 .name   = _NBT_NAME("_GA_GA_SI_U", 0x00, NULL),
6938                 .wins   = {
6939                         .nb_flags       = NBT_NM_GROUP,
6940                         .mhomed         = False,
6941                         .num_ips        = ctx->addresses_best_num,
6942                         .ips            = ctx->addresses_best,
6943                         .apply_expected = True
6944                 },
6945                 .defend = {
6946                         .timeout        = 0,
6947                 },
6948                 .replica= {
6949                         .type           = WREPL_TYPE_GROUP,
6950                         .state          = WREPL_STATE_ACTIVE,
6951                         .node           = WREPL_NODE_B,
6952                         .is_static      = False,
6953                         .num_ips        = ctx->addresses_best_num,
6954                         .ips            = ctx->addresses_best,
6955                         .apply_expected = True
6956                 },
6957         },
6958         /*
6959          * group,active vs. group,active with different ip(s), unchecked
6960          */
6961         {
6962                 .line   = __location__,
6963                 .name   = _NBT_NAME("_GA_GA_DI_U", 0x00, NULL),
6964                 .wins   = {
6965                         .nb_flags       = NBT_NM_GROUP,
6966                         .mhomed         = False,
6967                         .num_ips        = ctx->addresses_best_num,
6968                         .ips            = ctx->addresses_best,
6969                         .apply_expected = True
6970                 },
6971                 .defend = {
6972                         .timeout        = 0,
6973                 },
6974                 .replica= {
6975                         .type           = WREPL_TYPE_GROUP,
6976                         .state          = WREPL_STATE_ACTIVE,
6977                         .node           = WREPL_NODE_B,
6978                         .is_static      = False,
6979                         .num_ips        = ARRAY_SIZE(addresses_B_1),
6980                         .ips            = addresses_B_1,
6981                         .apply_expected = True
6982                 },
6983         },
6984         /*
6985          * group,active vs. group,tombstone with same ip(s), unchecked
6986          */
6987         {
6988                 .line   = __location__,
6989                 .name   = _NBT_NAME("_GA_GT_SI_U", 0x00, NULL),
6990                 .wins   = {
6991                         .nb_flags       = NBT_NM_GROUP,
6992                         .mhomed         = False,
6993                         .num_ips        = ctx->addresses_best_num,
6994                         .ips            = ctx->addresses_best,
6995                         .apply_expected = True
6996                 },
6997                 .defend = {
6998                         .timeout        = 0,
6999                 },
7000                 .replica= {
7001                         .type           = WREPL_TYPE_GROUP,
7002                         .state          = WREPL_STATE_TOMBSTONE,
7003                         .node           = WREPL_NODE_B,
7004                         .is_static      = False,
7005                         .num_ips        = ctx->addresses_best_num,
7006                         .ips            = ctx->addresses_best,
7007                         .apply_expected = False
7008                 },
7009         },
7010         /*
7011          * group,active vs. group,tombstone with different ip(s), unchecked
7012          */
7013         {
7014                 .line   = __location__,
7015                 .name   = _NBT_NAME("_GA_GT_DI_U", 0x00, NULL),
7016                 .wins   = {
7017                         .nb_flags       = NBT_NM_GROUP,
7018                         .mhomed         = False,
7019                         .num_ips        = ctx->addresses_best_num,
7020                         .ips            = ctx->addresses_best,
7021                         .apply_expected = True
7022                 },
7023                 .defend = {
7024                         .timeout        = 0,
7025                 },
7026                 .replica= {
7027                         .type           = WREPL_TYPE_GROUP,
7028                         .state          = WREPL_STATE_TOMBSTONE,
7029                         .node           = WREPL_NODE_B,
7030                         .is_static      = False,
7031                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7032                         .ips            = addresses_B_1,
7033                         .apply_expected = False
7034                 },
7035         },
7036 /* 
7037  * normal group vs. special group section
7038  */
7039         /*
7040          * group,active vs. sgroup,active with same ip(s), unchecked
7041          */
7042         {
7043                 .line   = __location__,
7044                 .name   = _NBT_NAME("_GA_SA_SI_U", 0x00, NULL),
7045                 .wins   = {
7046                         .nb_flags       = NBT_NM_GROUP,
7047                         .mhomed         = False,
7048                         .num_ips        = ctx->addresses_best_num,
7049                         .ips            = ctx->addresses_best,
7050                         .apply_expected = True
7051                 },
7052                 .defend = {
7053                         .timeout        = 0,
7054                 },
7055                 .replica= {
7056                         .type           = WREPL_TYPE_SGROUP,
7057                         .state          = WREPL_STATE_ACTIVE,
7058                         .node           = WREPL_NODE_B,
7059                         .is_static      = False,
7060                         .num_ips        = ctx->addresses_best_num,
7061                         .ips            = ctx->addresses_best,
7062                         .apply_expected = False
7063                 },
7064         },
7065         /*
7066          * group,active vs. sgroup,active with different ip(s), unchecked
7067          */
7068         {
7069                 .line   = __location__,
7070                 .name   = _NBT_NAME("_GA_SA_DI_U", 0x00, NULL),
7071                 .wins   = {
7072                         .nb_flags       = NBT_NM_GROUP,
7073                         .mhomed         = False,
7074                         .num_ips        = ctx->addresses_best_num,
7075                         .ips            = ctx->addresses_best,
7076                         .apply_expected = True
7077                 },
7078                 .defend = {
7079                         .timeout        = 0,
7080                 },
7081                 .replica= {
7082                         .type           = WREPL_TYPE_SGROUP,
7083                         .state          = WREPL_STATE_ACTIVE,
7084                         .node           = WREPL_NODE_B,
7085                         .is_static      = False,
7086                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
7087                         .ips            = addresses_B_3_4,
7088                         .apply_expected = False
7089                 },
7090         },
7091         /*
7092          * group,active vs. sgroup,tombstone with same ip(s), unchecked
7093          */
7094         {
7095                 .line   = __location__,
7096                 .name   = _NBT_NAME("_GA_ST_SI_U", 0x00, NULL),
7097                 .wins   = {
7098                         .nb_flags       = NBT_NM_GROUP,
7099                         .mhomed         = False,
7100                         .num_ips        = ctx->addresses_best_num,
7101                         .ips            = ctx->addresses_best,
7102                         .apply_expected = True
7103                 },
7104                 .defend = {
7105                         .timeout        = 0,
7106                 },
7107                 .replica= {
7108                         .type           = WREPL_TYPE_SGROUP,
7109                         .state          = WREPL_STATE_TOMBSTONE,
7110                         .node           = WREPL_NODE_B,
7111                         .is_static      = False,
7112                         .num_ips        = ctx->addresses_best_num,
7113                         .ips            = ctx->addresses_best,
7114                         .apply_expected = False
7115                 },
7116         },
7117         /*
7118          * group,active vs. sgroup,tombstone with different ip(s), unchecked
7119          */
7120         {
7121                 .line   = __location__,
7122                 .name   = _NBT_NAME("_GA_ST_DI_U", 0x00, NULL),
7123                 .wins   = {
7124                         .nb_flags       = NBT_NM_GROUP,
7125                         .mhomed         = False,
7126                         .num_ips        = ctx->addresses_best_num,
7127                         .ips            = ctx->addresses_best,
7128                         .apply_expected = True
7129                 },
7130                 .defend = {
7131                         .timeout        = 0,
7132                 },
7133                 .replica= {
7134                         .type           = WREPL_TYPE_SGROUP,
7135                         .state          = WREPL_STATE_TOMBSTONE,
7136                         .node           = WREPL_NODE_B,
7137                         .is_static      = False,
7138                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
7139                         .ips            = addresses_B_3_4,
7140                         .apply_expected = False
7141                 },
7142         },
7143 /* 
7144  * normal group vs. multi homed section
7145  */
7146         /*
7147          * group,active vs. mhomed,active with same ip(s), unchecked
7148          */
7149         {
7150                 .line   = __location__,
7151                 .name   = _NBT_NAME("_GA_MA_SI_U", 0x00, NULL),
7152                 .wins   = {
7153                         .nb_flags       = NBT_NM_GROUP,
7154                         .mhomed         = False,
7155                         .num_ips        = ctx->addresses_best_num,
7156                         .ips            = ctx->addresses_best,
7157                         .apply_expected = True
7158                 },
7159                 .defend = {
7160                         .timeout        = 0,
7161                 },
7162                 .replica= {
7163                         .type           = WREPL_TYPE_MHOMED,
7164                         .state          = WREPL_STATE_ACTIVE,
7165                         .node           = WREPL_NODE_B,
7166                         .is_static      = False,
7167                         .num_ips        = ctx->addresses_best_num,
7168                         .ips            = ctx->addresses_best,
7169                         .apply_expected = False
7170                 },
7171         },
7172         /*
7173          * group,active vs. mhomed,active with different ip(s), unchecked
7174          */
7175         {
7176                 .line   = __location__,
7177                 .name   = _NBT_NAME("_GA_MA_DI_U", 0x00, NULL),
7178                 .wins   = {
7179                         .nb_flags       = NBT_NM_GROUP,
7180                         .mhomed         = False,
7181                         .num_ips        = ctx->addresses_best_num,
7182                         .ips            = ctx->addresses_best,
7183                         .apply_expected = True
7184                 },
7185                 .defend = {
7186                         .timeout        = 0,
7187                 },
7188                 .replica= {
7189                         .type           = WREPL_TYPE_MHOMED,
7190                         .state          = WREPL_STATE_ACTIVE,
7191                         .node           = WREPL_NODE_B,
7192                         .is_static      = False,
7193                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
7194                         .ips            = addresses_B_3_4,
7195                         .apply_expected = False
7196                 },
7197         },
7198         /*
7199          * group,active vs. mhomed,tombstone with same ip(s), unchecked
7200          */
7201         {
7202                 .line   = __location__,
7203                 .name   = _NBT_NAME("_GA_MT_SI_U", 0x00, NULL),
7204                 .wins   = {
7205                         .nb_flags       = NBT_NM_GROUP,
7206                         .mhomed         = False,
7207                         .num_ips        = ctx->addresses_best_num,
7208                         .ips            = ctx->addresses_best,
7209                         .apply_expected = True
7210                 },
7211                 .defend = {
7212                         .timeout        = 0,
7213                 },
7214                 .replica= {
7215                         .type           = WREPL_TYPE_MHOMED,
7216                         .state          = WREPL_STATE_TOMBSTONE,
7217                         .node           = WREPL_NODE_B,
7218                         .is_static      = False,
7219                         .num_ips        = ctx->addresses_best_num,
7220                         .ips            = ctx->addresses_best,
7221                         .apply_expected = False
7222                 },
7223         },
7224         /*
7225          * group,active vs. mhomed,tombstone with different ip(s), unchecked
7226          */
7227         {
7228                 .line   = __location__,
7229                 .name   = _NBT_NAME("_GA_MT_DI_U", 0x00, NULL),
7230                 .wins   = {
7231                         .nb_flags       = NBT_NM_GROUP,
7232                         .mhomed         = False,
7233                         .num_ips        = ctx->addresses_best_num,
7234                         .ips            = ctx->addresses_best,
7235                         .apply_expected = True
7236                 },
7237                 .defend = {
7238                         .timeout        = 0,
7239                 },
7240                 .replica= {
7241                         .type           = WREPL_TYPE_MHOMED,
7242                         .state          = WREPL_STATE_TOMBSTONE,
7243                         .node           = WREPL_NODE_B,
7244                         .is_static      = False,
7245                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
7246                         .ips            = addresses_B_3_4,
7247                         .apply_expected = False
7248                 },
7249         },
7250 /* 
7251  * special group vs. unique section
7252  */
7253         /*
7254          * sgroup,active vs. unique,active with same ip(s), unchecked
7255          */
7256         {
7257                 .line   = __location__,
7258                 .name   = _NBT_NAME("_SA_UA_SI_U", 0x1C, NULL),
7259                 .wins   = {
7260                         .nb_flags       = NBT_NM_GROUP,
7261                         .mhomed         = False,
7262                         .num_ips        = ctx->addresses_best_num,
7263                         .ips            = ctx->addresses_best,
7264                         .apply_expected = True
7265                 },
7266                 .defend = {
7267                         .timeout        = 0,
7268                 },
7269                 .replica= {
7270                         .type           = WREPL_TYPE_UNIQUE,
7271                         .state          = WREPL_STATE_ACTIVE,
7272                         .node           = WREPL_NODE_B,
7273                         .is_static      = False,
7274                         .num_ips        = ctx->addresses_best_num,
7275                         .ips            = ctx->addresses_best,
7276                         .apply_expected = False
7277                 },
7278         },
7279         /*
7280          * sgroup,active vs. unique,active with different ip(s), unchecked
7281          */
7282         {
7283                 .line   = __location__,
7284                 .name   = _NBT_NAME("_SA_UA_DI_U", 0x1C, NULL),
7285                 .wins   = {
7286                         .nb_flags       = NBT_NM_GROUP,
7287                         .mhomed         = False,
7288                         .num_ips        = ctx->addresses_best_num,
7289                         .ips            = ctx->addresses_best,
7290                         .apply_expected = True
7291                 },
7292                 .defend = {
7293                         .timeout        = 0,
7294                 },
7295                 .replica= {
7296                         .type           = WREPL_TYPE_UNIQUE,
7297                         .state          = WREPL_STATE_ACTIVE,
7298                         .node           = WREPL_NODE_B,
7299                         .is_static      = False,
7300                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7301                         .ips            = addresses_B_1,
7302                         .apply_expected = False
7303                 },
7304         },
7305         /*
7306          * sgroup,active vs. unique,tombstone with same ip(s), unchecked
7307          */
7308         {
7309                 .line   = __location__,
7310                 .name   = _NBT_NAME("_SA_UT_SI_U", 0x1C, NULL),
7311                 .wins   = {
7312                         .nb_flags       = NBT_NM_GROUP,
7313                         .mhomed         = False,
7314                         .num_ips        = ctx->addresses_best_num,
7315                         .ips            = ctx->addresses_best,
7316                         .apply_expected = True
7317                 },
7318                 .defend = {
7319                         .timeout        = 0,
7320                 },
7321                 .replica= {
7322                         .type           = WREPL_TYPE_UNIQUE,
7323                         .state          = WREPL_STATE_TOMBSTONE,
7324                         .node           = WREPL_NODE_B,
7325                         .is_static      = False,
7326                         .num_ips        = ctx->addresses_best_num,
7327                         .ips            = ctx->addresses_best,
7328                         .apply_expected = False
7329                 },
7330         },
7331         /*
7332          * sgroup,active vs. unique,tombstone with different ip(s), unchecked
7333          */
7334         {
7335                 .line   = __location__,
7336                 .name   = _NBT_NAME("_SA_UT_DI_U", 0x1C, NULL),
7337                 .wins   = {
7338                         .nb_flags       = NBT_NM_GROUP,
7339                         .mhomed         = False,
7340                         .num_ips        = ctx->addresses_best_num,
7341                         .ips            = ctx->addresses_best,
7342                         .apply_expected = True
7343                 },
7344                 .defend = {
7345                         .timeout        = 0,
7346                 },
7347                 .replica= {
7348                         .type           = WREPL_TYPE_UNIQUE,
7349                         .state          = WREPL_STATE_TOMBSTONE,
7350                         .node           = WREPL_NODE_B,
7351                         .is_static      = False,
7352                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7353                         .ips            = addresses_B_1,
7354                         .apply_expected = False
7355                 },
7356         },
7357 /* 
7358  * special group vs. normal group section
7359  */
7360         /*
7361          * sgroup,active vs. group,active with same ip(s), unchecked
7362          */
7363         {
7364                 .line   = __location__,
7365                 .name   = _NBT_NAME("_SA_GA_SI_U", 0x1C, NULL),
7366                 .wins   = {
7367                         .nb_flags       = NBT_NM_GROUP,
7368                         .mhomed         = False,
7369                         .num_ips        = ctx->addresses_best_num,
7370                         .ips            = ctx->addresses_best,
7371                         .apply_expected = True
7372                 },
7373                 .defend = {
7374                         .timeout        = 0,
7375                 },
7376                 .replica= {
7377                         .type           = WREPL_TYPE_GROUP,
7378                         .state          = WREPL_STATE_ACTIVE,
7379                         .node           = WREPL_NODE_B,
7380                         .is_static      = False,
7381                         .num_ips        = ctx->addresses_best_num,
7382                         .ips            = ctx->addresses_best,
7383                         .apply_expected = False
7384                 },
7385         },
7386         /*
7387          * sgroup,active vs. group,active with different ip(s), unchecked
7388          */
7389         {
7390                 .line   = __location__,
7391                 .name   = _NBT_NAME("_SA_GA_DI_U", 0x1C, NULL),
7392                 .wins   = {
7393                         .nb_flags       = NBT_NM_GROUP,
7394                         .mhomed         = False,
7395                         .num_ips        = ctx->addresses_best_num,
7396                         .ips            = ctx->addresses_best,
7397                         .apply_expected = True
7398                 },
7399                 .defend = {
7400                         .timeout        = 0,
7401                 },
7402                 .replica= {
7403                         .type           = WREPL_TYPE_GROUP,
7404                         .state          = WREPL_STATE_ACTIVE,
7405                         .node           = WREPL_NODE_B,
7406                         .is_static      = False,
7407                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7408                         .ips            = addresses_B_1,
7409                         .apply_expected = False
7410                 },
7411         },
7412         /*
7413          * sgroup,active vs. group,tombstone with same ip(s), unchecked
7414          */
7415         {
7416                 .line   = __location__,
7417                 .name   = _NBT_NAME("_SA_GT_SI_U", 0x1C, NULL),
7418                 .wins   = {
7419                         .nb_flags       = NBT_NM_GROUP,
7420                         .mhomed         = False,
7421                         .num_ips        = ctx->addresses_best_num,
7422                         .ips            = ctx->addresses_best,
7423                         .apply_expected = True
7424                 },
7425                 .defend = {
7426                         .timeout        = 0,
7427                 },
7428                 .replica= {
7429                         .type           = WREPL_TYPE_GROUP,
7430                         .state          = WREPL_STATE_TOMBSTONE,
7431                         .node           = WREPL_NODE_B,
7432                         .is_static      = False,
7433                         .num_ips        = ctx->addresses_best_num,
7434                         .ips            = ctx->addresses_best,
7435                         .apply_expected = False
7436                 },
7437         },
7438         /*
7439          * sgroup,active vs. group,tombstone with different ip(s), unchecked
7440          */
7441         {
7442                 .line   = __location__,
7443                 .name   = _NBT_NAME("_SA_GT_DI_U", 0x1C, NULL),
7444                 .wins   = {
7445                         .nb_flags       = NBT_NM_GROUP,
7446                         .mhomed         = False,
7447                         .num_ips        = ctx->addresses_best_num,
7448                         .ips            = ctx->addresses_best,
7449                         .apply_expected = True
7450                 },
7451                 .defend = {
7452                         .timeout        = 0,
7453                 },
7454                 .replica= {
7455                         .type           = WREPL_TYPE_GROUP,
7456                         .state          = WREPL_STATE_TOMBSTONE,
7457                         .node           = WREPL_NODE_B,
7458                         .is_static      = False,
7459                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7460                         .ips            = addresses_B_1,
7461                         .apply_expected = False
7462                 },
7463         },
7464 /* 
7465  * special group vs. multi homed section
7466  */
7467         /*
7468          * sgroup,active vs. mhomed,active with same ip(s), unchecked
7469          */
7470         {
7471                 .line   = __location__,
7472                 .name   = _NBT_NAME("_SA_MA_SI_U", 0x1C, NULL),
7473                 .wins   = {
7474                         .nb_flags       = NBT_NM_GROUP,
7475                         .mhomed         = False,
7476                         .num_ips        = ctx->addresses_best_num,
7477                         .ips            = ctx->addresses_best,
7478                         .apply_expected = True
7479                 },
7480                 .defend = {
7481                         .timeout        = 0,
7482                 },
7483                 .replica= {
7484                         .type           = WREPL_TYPE_MHOMED,
7485                         .state          = WREPL_STATE_ACTIVE,
7486                         .node           = WREPL_NODE_B,
7487                         .is_static      = False,
7488                         .num_ips        = ctx->addresses_best_num,
7489                         .ips            = ctx->addresses_best,
7490                         .apply_expected = False
7491                 },
7492         },
7493         /*
7494          * sgroup,active vs. mhomed,active with different ip(s), unchecked
7495          */
7496         {
7497                 .line   = __location__,
7498                 .name   = _NBT_NAME("_SA_MA_DI_U", 0x1C, NULL),
7499                 .wins   = {
7500                         .nb_flags       = NBT_NM_GROUP,
7501                         .mhomed         = False,
7502                         .num_ips        = ctx->addresses_best_num,
7503                         .ips            = ctx->addresses_best,
7504                         .apply_expected = True
7505                 },
7506                 .defend = {
7507                         .timeout        = 0,
7508                 },
7509                 .replica= {
7510                         .type           = WREPL_TYPE_MHOMED,
7511                         .state          = WREPL_STATE_ACTIVE,
7512                         .node           = WREPL_NODE_B,
7513                         .is_static      = False,
7514                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7515                         .ips            = addresses_B_1,
7516                         .apply_expected = False
7517                 },
7518         },
7519         /*
7520          * sgroup,active vs. mhomed,tombstone with same ip(s), unchecked
7521          */
7522         {
7523                 .line   = __location__,
7524                 .name   = _NBT_NAME("_SA_MT_SI_U", 0x1C, NULL),
7525                 .wins   = {
7526                         .nb_flags       = NBT_NM_GROUP,
7527                         .mhomed         = False,
7528                         .num_ips        = ctx->addresses_best_num,
7529                         .ips            = ctx->addresses_best,
7530                         .apply_expected = True
7531                 },
7532                 .defend = {
7533                         .timeout        = 0,
7534                 },
7535                 .replica= {
7536                         .type           = WREPL_TYPE_MHOMED,
7537                         .state          = WREPL_STATE_TOMBSTONE,
7538                         .node           = WREPL_NODE_B,
7539                         .is_static      = False,
7540                         .num_ips        = ctx->addresses_best_num,
7541                         .ips            = ctx->addresses_best,
7542                         .apply_expected = False
7543                 },
7544         },
7545         /*
7546          * sgroup,active vs. mhomed,tombstone with different ip(s), unchecked
7547          */
7548         {
7549                 .line   = __location__,
7550                 .name   = _NBT_NAME("_SA_MT_DI_U", 0x1C, NULL),
7551                 .wins   = {
7552                         .nb_flags       = NBT_NM_GROUP,
7553                         .mhomed         = False,
7554                         .num_ips        = ctx->addresses_best_num,
7555                         .ips            = ctx->addresses_best,
7556                         .apply_expected = True
7557                 },
7558                 .defend = {
7559                         .timeout        = 0,
7560                 },
7561                 .replica= {
7562                         .type           = WREPL_TYPE_MHOMED,
7563                         .state          = WREPL_STATE_TOMBSTONE,
7564                         .node           = WREPL_NODE_B,
7565                         .is_static      = False,
7566                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7567                         .ips            = addresses_B_1,
7568                         .apply_expected = False
7569                 },
7570         },
7571 /* 
7572  * multi homed vs. unique section
7573  */
7574         /*
7575          * mhomed,active vs. unique,active with same ip(s), unchecked
7576          */
7577         {
7578                 .line   = __location__,
7579                 .name   = _NBT_NAME("_MA_UA_SI_U", 0x00, NULL),
7580                 .wins   = {
7581                         .nb_flags       = 0,
7582                         .mhomed         = True,
7583                         .num_ips        = ctx->addresses_best_num,
7584                         .ips            = ctx->addresses_best,
7585                         .apply_expected = True
7586                 },
7587                 .defend = {
7588                         .timeout        = 0,
7589                 },
7590                 .replica= {
7591                         .type           = WREPL_TYPE_UNIQUE,
7592                         .state          = WREPL_STATE_ACTIVE,
7593                         .node           = WREPL_NODE_B,
7594                         .is_static      = False,
7595                         .num_ips        = ctx->addresses_best_num,
7596                         .ips            = ctx->addresses_best,
7597                         .apply_expected = True
7598                 },
7599         },
7600         /*
7601          * mhomed,active vs. unique,active with different ip(s), positive response
7602          */
7603         {
7604                 .line   = __location__,
7605                 .name   = _NBT_NAME("_MA_UA_DI_P", 0x00, NULL),
7606                 .wins   = {
7607                         .nb_flags       = 0,
7608                         .mhomed         = True,
7609                         .num_ips        = ctx->addresses_best_num,
7610                         .ips            = ctx->addresses_best,
7611                         .apply_expected = True
7612                 },
7613                 .defend = {
7614                         .timeout        = 10,
7615                         .positive       = True,
7616                 },
7617                 .replica= {
7618                         .type           = WREPL_TYPE_UNIQUE,
7619                         .state          = WREPL_STATE_ACTIVE,
7620                         .node           = WREPL_NODE_B,
7621                         .is_static      = False,
7622                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7623                         .ips            = addresses_B_1,
7624                         .apply_expected = False
7625                 },
7626         },
7627         /*
7628          * mhomed,active vs. unique,active with different ip(s), positive response other ips
7629          */
7630         {
7631                 .line   = __location__,
7632                 .name   = _NBT_NAME("_MA_UA_DI_O", 0x00, NULL),
7633                 .wins   = {
7634                         .nb_flags       = 0,
7635                         .mhomed         = True,
7636                         .num_ips        = ctx->addresses_best_num,
7637                         .ips            = ctx->addresses_best,
7638                         .apply_expected = True
7639                 },
7640                 .defend = {
7641                         .timeout        = 10,
7642                         .positive       = True,
7643                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
7644                         .ips            = addresses_A_3_4,
7645                 },
7646                 .replica= {
7647                         .type           = WREPL_TYPE_UNIQUE,
7648                         .state          = WREPL_STATE_ACTIVE,
7649                         .node           = WREPL_NODE_B,
7650                         .is_static      = False,
7651                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7652                         .ips            = addresses_B_1,
7653                         .apply_expected = False
7654                 },
7655         },
7656         /*
7657          * mhomed,active vs. unique,active with different ip(s), negative response
7658          */
7659         {
7660                 .line   = __location__,
7661                 .name   = _NBT_NAME("_MA_UA_DI_N", 0x00, NULL),
7662                 .wins   = {
7663                         .nb_flags       = 0,
7664                         .mhomed         = True,
7665                         .num_ips        = ctx->addresses_best_num,
7666                         .ips            = ctx->addresses_best,
7667                         .apply_expected = True
7668                 },
7669                 .defend = {
7670                         .timeout        = 10,
7671                         .positive       = False,
7672                 },
7673                 .replica= {
7674                         .type           = WREPL_TYPE_UNIQUE,
7675                         .state          = WREPL_STATE_ACTIVE,
7676                         .node           = WREPL_NODE_B,
7677                         .is_static      = False,
7678                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7679                         .ips            = addresses_B_1,
7680                         .apply_expected = True
7681                 },
7682         },
7683         /*
7684          * mhomed,active vs. unique,tombstone with same ip(s), unchecked
7685          */
7686         {
7687                 .line   = __location__,
7688                 .name   = _NBT_NAME("_MA_UT_SI_U", 0x00, NULL),
7689                 .wins   = {
7690                         .nb_flags       = 0,
7691                         .mhomed         = True,
7692                         .num_ips        = ctx->addresses_best_num,
7693                         .ips            = ctx->addresses_best,
7694                         .apply_expected = True
7695                 },
7696                 .defend = {
7697                         .timeout        = 0,
7698                 },
7699                 .replica= {
7700                         .type           = WREPL_TYPE_UNIQUE,
7701                         .state          = WREPL_STATE_TOMBSTONE,
7702                         .node           = WREPL_NODE_B,
7703                         .is_static      = False,
7704                         .num_ips        = ctx->addresses_best_num,
7705                         .ips            = ctx->addresses_best,
7706                         .apply_expected = False
7707                 },
7708         },
7709         /*
7710          * mhomed,active vs. unique,tombstone with different ip(s), unchecked
7711          */
7712         {
7713                 .line   = __location__,
7714                 .name   = _NBT_NAME("_MA_UT_DI_U", 0x00, NULL),
7715                 .wins   = {
7716                         .nb_flags       = 0,
7717                         .mhomed         = True,
7718                         .num_ips        = ctx->addresses_best_num,
7719                         .ips            = ctx->addresses_best,
7720                         .apply_expected = True
7721                 },
7722                 .defend = {
7723                         .timeout        = 0,
7724                 },
7725                 .replica= {
7726                         .type           = WREPL_TYPE_UNIQUE,
7727                         .state          = WREPL_STATE_TOMBSTONE,
7728                         .node           = WREPL_NODE_B,
7729                         .is_static      = False,
7730                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7731                         .ips            = addresses_B_1,
7732                         .apply_expected = False
7733                 },
7734         },
7735 /* 
7736  * multi homed vs. normal group section
7737  */
7738         /*
7739          * mhomed,active vs. group,active with same ip(s), release expected
7740          */
7741         {
7742                 .line   = __location__,
7743                 .name   = _NBT_NAME("_MA_GA_SI_R", 0x00, NULL),
7744                 .wins   = {
7745                         .nb_flags       = 0,
7746                         .mhomed         = True,
7747                         .num_ips        = ctx->addresses_best_num,
7748                         .ips            = ctx->addresses_best,
7749                         .apply_expected = True
7750                 },
7751                 .defend = {
7752                         .timeout        = 10,
7753                         .expect_release = True,
7754                 },
7755                 .replica= {
7756                         .type           = WREPL_TYPE_GROUP,
7757                         .state          = WREPL_STATE_ACTIVE,
7758                         .node           = WREPL_NODE_B,
7759                         .is_static      = False,
7760                         .num_ips        = ctx->addresses_best_num,
7761                         .ips            = ctx->addresses_best,
7762                         .apply_expected = True
7763                 },
7764         },
7765         /*
7766          * mhomed,active vs. group,active with different ip(s), release expected
7767          */
7768         {
7769                 .line   = __location__,
7770                 .name   = _NBT_NAME("_MA_GA_DI_R", 0x00, NULL),
7771                 .wins   = {
7772                         .nb_flags       = 0,
7773                         .mhomed         = True,
7774                         .num_ips        = ctx->addresses_best_num,
7775                         .ips            = ctx->addresses_best,
7776                         .apply_expected = True
7777                 },
7778                 .defend = {
7779                         .timeout        = 10,
7780                         .expect_release = True,
7781                 },
7782                 .replica= {
7783                         .type           = WREPL_TYPE_GROUP,
7784                         .state          = WREPL_STATE_ACTIVE,
7785                         .node           = WREPL_NODE_B,
7786                         .is_static      = False,
7787                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7788                         .ips            = addresses_B_1,
7789                         .apply_expected = True
7790                 },
7791         },
7792         /*
7793          * mhomed,active vs. group,tombstone with same ip(s), unchecked
7794          */
7795         {
7796                 .line   = __location__,
7797                 .name   = _NBT_NAME("_MA_GT_SI_U", 0x00, NULL),
7798                 .wins   = {
7799                         .nb_flags       = 0,
7800                         .mhomed         = True,
7801                         .num_ips        = ctx->addresses_best_num,
7802                         .ips            = ctx->addresses_best,
7803                         .apply_expected = True
7804                 },
7805                 .defend = {
7806                         .timeout        = 0,
7807                 },
7808                 .replica= {
7809                         .type           = WREPL_TYPE_GROUP,
7810                         .state          = WREPL_STATE_TOMBSTONE,
7811                         .node           = WREPL_NODE_B,
7812                         .is_static      = False,
7813                         .num_ips        = ctx->addresses_best_num,
7814                         .ips            = ctx->addresses_best,
7815                         .apply_expected = False
7816                 },
7817         },
7818         /*
7819          * mhomed,active vs. group,tombstone with different ip(s), unchecked
7820          */
7821         {
7822                 .line   = __location__,
7823                 .name   = _NBT_NAME("_MA_GT_DI_U", 0x00, NULL),
7824                 .wins   = {
7825                         .nb_flags       = 0,
7826                         .mhomed         = True,
7827                         .num_ips        = ctx->addresses_best_num,
7828                         .ips            = ctx->addresses_best,
7829                         .apply_expected = True
7830                 },
7831                 .defend = {
7832                         .timeout        = 0,
7833                 },
7834                 .replica= {
7835                         .type           = WREPL_TYPE_GROUP,
7836                         .state          = WREPL_STATE_TOMBSTONE,
7837                         .node           = WREPL_NODE_B,
7838                         .is_static      = False,
7839                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7840                         .ips            = addresses_B_1,
7841                         .apply_expected = False
7842                 },
7843         },
7844 /* 
7845  * multi homed vs. special group section
7846  */
7847         /*
7848          * mhomed,active vs. sgroup,active with same ip(s), release expected
7849          */
7850         {
7851                 .line   = __location__,
7852                 .name   = _NBT_NAME("_MA_SA_SI_R", 0x00, NULL),
7853                 .wins   = {
7854                         .nb_flags       = 0,
7855                         .mhomed         = True,
7856                         .num_ips        = ctx->addresses_best_num,
7857                         .ips            = ctx->addresses_best,
7858                         .apply_expected = True
7859                 },
7860                 .defend = {
7861                         .timeout        = 10,
7862                         .expect_release = True,
7863                 },
7864                 .replica= {
7865                         .type           = WREPL_TYPE_SGROUP,
7866                         .state          = WREPL_STATE_ACTIVE,
7867                         .node           = WREPL_NODE_B,
7868                         .is_static      = False,
7869                         .num_ips        = ctx->addresses_best_num,
7870                         .ips            = ctx->addresses_best,
7871                         .apply_expected = True
7872                 },
7873         },
7874         /*
7875          * mhomed,active vs. group,active with different ip(s), release expected
7876          */
7877         {
7878                 .line   = __location__,
7879                 .name   = _NBT_NAME("_MA_SA_DI_R", 0x00, NULL),
7880                 .wins   = {
7881                         .nb_flags       = 0,
7882                         .mhomed         = True,
7883                         .num_ips        = ctx->addresses_best_num,
7884                         .ips            = ctx->addresses_best,
7885                         .apply_expected = True
7886                 },
7887                 .defend = {
7888                         .timeout        = 10,
7889                         .expect_release = True,
7890                 },
7891                 .replica= {
7892                         .type           = WREPL_TYPE_SGROUP,
7893                         .state          = WREPL_STATE_ACTIVE,
7894                         .node           = WREPL_NODE_B,
7895                         .is_static      = False,
7896                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7897                         .ips            = addresses_B_1,
7898                         .apply_expected = True
7899                 },
7900         },
7901         /*
7902          * mhomed,active vs. sgroup,tombstone with same ip(s), unchecked
7903          */
7904         {
7905                 .line   = __location__,
7906                 .name   = _NBT_NAME("_MA_ST_SI_U", 0x00, NULL),
7907                 .wins   = {
7908                         .nb_flags       = 0,
7909                         .mhomed         = True,
7910                         .num_ips        = ctx->addresses_best_num,
7911                         .ips            = ctx->addresses_best,
7912                         .apply_expected = True
7913                 },
7914                 .defend = {
7915                         .timeout        = 0,
7916                 },
7917                 .replica= {
7918                         .type           = WREPL_TYPE_SGROUP,
7919                         .state          = WREPL_STATE_TOMBSTONE,
7920                         .node           = WREPL_NODE_B,
7921                         .is_static      = False,
7922                         .num_ips        = ctx->addresses_best_num,
7923                         .ips            = ctx->addresses_best,
7924                         .apply_expected = False
7925                 },
7926         },
7927         /*
7928          * mhomed,active vs. sgroup,tombstone with different ip(s), unchecked
7929          */
7930         {
7931                 .line   = __location__,
7932                 .name   = _NBT_NAME("_MA_ST_DI_U", 0x00, NULL),
7933                 .wins   = {
7934                         .nb_flags       = 0,
7935                         .mhomed         = True,
7936                         .num_ips        = ctx->addresses_best_num,
7937                         .ips            = ctx->addresses_best,
7938                         .apply_expected = True
7939                 },
7940                 .defend = {
7941                         .timeout        = 0,
7942                 },
7943                 .replica= {
7944                         .type           = WREPL_TYPE_SGROUP,
7945                         .state          = WREPL_STATE_TOMBSTONE,
7946                         .node           = WREPL_NODE_B,
7947                         .is_static      = False,
7948                         .num_ips        = ARRAY_SIZE(addresses_B_1),
7949                         .ips            = addresses_B_1,
7950                         .apply_expected = False
7951                 },
7952         },
7953 /* 
7954  * multi homed vs. multi homed section
7955  */
7956         /*
7957          * mhomed,active vs. mhomed,active with same ip(s), unchecked
7958          */
7959         {
7960                 .line   = __location__,
7961                 .name   = _NBT_NAME("_MA_MA_SI_U", 0x00, NULL),
7962                 .wins   = {
7963                         .nb_flags       = 0,
7964                         .mhomed         = True,
7965                         .num_ips        = ctx->addresses_best_num,
7966                         .ips            = ctx->addresses_best,
7967                         .apply_expected = True
7968                 },
7969                 .defend = {
7970                         .timeout        = 0,
7971                 },
7972                 .replica= {
7973                         .type           = WREPL_TYPE_MHOMED,
7974                         .state          = WREPL_STATE_ACTIVE,
7975                         .node           = WREPL_NODE_B,
7976                         .is_static      = False,
7977                         .num_ips        = ctx->addresses_best_num,
7978                         .ips            = ctx->addresses_best,
7979                         .apply_expected = True
7980                 },
7981         },
7982         /*
7983          * mhomed,active vs. mhomed,active with superset ip(s), unchecked
7984          */
7985         {
7986                 .line   = __location__,
7987                 .name   = _NBT_NAME("_MA_MA_SP_U", 0x00, NULL),
7988                 .wins   = {
7989                         .nb_flags       = 0,
7990                         .mhomed         = True,
7991                         .num_ips        = ctx->addresses_best_num,
7992                         .ips            = ctx->addresses_best,
7993                         .apply_expected = True
7994                 },
7995                 .defend = {
7996                         .timeout        = 0,
7997                 },
7998                 .replica= {
7999                         .type           = WREPL_TYPE_MHOMED,
8000                         .state          = WREPL_STATE_ACTIVE,
8001                         .node           = WREPL_NODE_B,
8002                         .is_static      = False,
8003                         .num_ips        = ctx->addresses_all_num,
8004                         .ips            = ctx->addresses_all,
8005                         .apply_expected = True
8006                 },
8007         },
8008         /*
8009          * mhomed,active vs. mhomed,active with different ip(s), positive response
8010          */
8011         {
8012                 .line   = __location__,
8013                 .name   = _NBT_NAME("_MA_MA_DI_P", 0x00, NULL),
8014                 .wins   = {
8015                         .nb_flags       = 0,
8016                         .mhomed         = True,
8017                         .num_ips        = ctx->addresses_best_num,
8018                         .ips            = ctx->addresses_best,
8019                         .apply_expected = True
8020                 },
8021                 .defend = {
8022                         .timeout        = 10,
8023                         .positive       = True,
8024                 },
8025                 .replica= {
8026                         .type           = WREPL_TYPE_MHOMED,
8027                         .state          = WREPL_STATE_ACTIVE,
8028                         .node           = WREPL_NODE_B,
8029                         .is_static      = False,
8030                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
8031                         .ips            = addresses_B_3_4,
8032                         .apply_expected = False
8033                 },
8034         },
8035         /*
8036          * mhomed,active vs. mhomed,active with different ip(s), positive response other ips
8037          */
8038         {
8039                 .line   = __location__,
8040                 .name   = _NBT_NAME("_MA_MA_DI_O", 0x00, NULL),
8041                 .wins   = {
8042                         .nb_flags       = 0,
8043                         .mhomed         = True,
8044                         .num_ips        = ctx->addresses_best_num,
8045                         .ips            = ctx->addresses_best,
8046                         .apply_expected = True
8047                 },
8048                 .defend = {
8049                         .timeout        = 10,
8050                         .positive       = True,
8051                         .num_ips        = ARRAY_SIZE(addresses_A_3_4),
8052                         .ips            = addresses_A_3_4,
8053                 },
8054                 .replica= {
8055                         .type           = WREPL_TYPE_MHOMED,
8056                         .state          = WREPL_STATE_ACTIVE,
8057                         .node           = WREPL_NODE_B,
8058                         .is_static      = False,
8059                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
8060                         .ips            = addresses_B_3_4,
8061                         .apply_expected = False
8062                 },
8063         },
8064         /*
8065          * mhomed,active vs. mhomed,active with different ip(s), negative response
8066          */
8067         {
8068                 .line   = __location__,
8069                 .name   = _NBT_NAME("_MA_MA_DI_N", 0x00, NULL),
8070                 .wins   = {
8071                         .nb_flags       = 0,
8072                         .mhomed         = True,
8073                         .num_ips        = ctx->addresses_best_num,
8074                         .ips            = ctx->addresses_best,
8075                         .apply_expected = True
8076                 },
8077                 .defend = {
8078                         .timeout        = 10,
8079                         .positive       = False,
8080                 },
8081                 .replica= {
8082                         .type           = WREPL_TYPE_MHOMED,
8083                         .state          = WREPL_STATE_ACTIVE,
8084                         .node           = WREPL_NODE_B,
8085                         .is_static      = False,
8086                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
8087                         .ips            = addresses_B_3_4,
8088                         .apply_expected = True
8089                 },
8090         },
8091         /*
8092          * mhomed,active vs. mhomed,tombstone with same ip(s), unchecked
8093          */
8094         {
8095                 .line   = __location__,
8096                 .name   = _NBT_NAME("_MA_MT_SI_U", 0x00, NULL),
8097                 .wins   = {
8098                         .nb_flags       = 0,
8099                         .mhomed         = True,
8100                         .num_ips        = ctx->addresses_best_num,
8101                         .ips            = ctx->addresses_best,
8102                         .apply_expected = True
8103                 },
8104                 .defend = {
8105                         .timeout        = 0,
8106                 },
8107                 .replica= {
8108                         .type           = WREPL_TYPE_MHOMED,
8109                         .state          = WREPL_STATE_TOMBSTONE,
8110                         .node           = WREPL_NODE_B,
8111                         .is_static      = False,
8112                         .num_ips        = ctx->addresses_best_num,
8113                         .ips            = ctx->addresses_best,
8114                         .apply_expected = False
8115                 },
8116         },
8117         /*
8118          * mhomed,active vs. mhomed,tombstone with different ip(s), unchecked
8119          */
8120         {
8121                 .line   = __location__,
8122                 .name   = _NBT_NAME("_MA_MT_DI_U", 0x00, NULL),
8123                 .wins   = {
8124                         .nb_flags       = 0,
8125                         .mhomed         = True,
8126                         .num_ips        = ctx->addresses_best_num,
8127                         .ips            = ctx->addresses_best,
8128                         .apply_expected = True
8129                 },
8130                 .defend = {
8131                         .timeout        = 0,
8132                 },
8133                 .replica= {
8134                         .type           = WREPL_TYPE_MHOMED,
8135                         .state          = WREPL_STATE_TOMBSTONE,
8136                         .node           = WREPL_NODE_B,
8137                         .is_static      = False,
8138                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
8139                         .ips            = addresses_B_3_4,
8140                         .apply_expected = False
8141                 },
8142         },
8143 /*
8144  * some more multi homed test, including merging
8145  */
8146         /*
8147          * mhomed,active vs. mhomed,active with superset ip(s), unchecked
8148          */
8149         {
8150                 .line   = __location__,
8151                 .section= "Test Replica vs. owned active: some more MHOMED combinations",
8152                 .name   = _NBT_NAME("_MA_MA_SP_U", 0x00, NULL),
8153                 .skip   = (ctx->addresses_all_num < 3),
8154                 .wins   = {
8155                         .nb_flags       = 0,
8156                         .mhomed         = True,
8157                         .num_ips        = ctx->addresses_mhomed_num,
8158                         .ips            = ctx->addresses_mhomed,
8159                         .apply_expected = True
8160                 },
8161                 .defend = {
8162                         .timeout        = 0,
8163                 },
8164                 .replica= {
8165                         .type           = WREPL_TYPE_MHOMED,
8166                         .state          = WREPL_STATE_ACTIVE,
8167                         .node           = WREPL_NODE_B,
8168                         .is_static      = False,
8169                         .num_ips        = ctx->addresses_all_num,
8170                         .ips            = ctx->addresses_all,
8171                         .apply_expected = True
8172                 },
8173         },
8174         /*
8175          * mhomed,active vs. mhomed,active with same ips, unchecked
8176          */
8177         {
8178                 .line   = __location__,
8179                 .name   = _NBT_NAME("_MA_MA_SM_U", 0x00, NULL),
8180                 .skip   = (ctx->addresses_mhomed_num != 2),
8181                 .wins   = {
8182                         .nb_flags       = 0,
8183                         .mhomed         = True,
8184                         .num_ips        = ctx->addresses_mhomed_num,
8185                         .ips            = ctx->addresses_mhomed,
8186                         .apply_expected = True
8187                 },
8188                 .defend = {
8189                         .timeout        = 0,
8190                 },
8191                 .replica= {
8192                         .type           = WREPL_TYPE_MHOMED,
8193                         .state          = WREPL_STATE_ACTIVE,
8194                         .node           = WREPL_NODE_B,
8195                         .is_static      = False,
8196                         .num_ips        = ctx->addresses_mhomed_num,
8197                         .ips            = ctx->addresses_mhomed,
8198                         .apply_expected = True
8199                 },
8200         },
8201         /*
8202          * mhomed,active vs. mhomed,active with subset ip(s), positive response
8203          */
8204         {
8205                 .line   = __location__,
8206                 .name   = _NBT_NAME("_MA_MA_SB_P", 0x00, NULL),
8207                 .skip   = (ctx->addresses_mhomed_num != 2),
8208                 .wins   = {
8209                         .nb_flags       = 0,
8210                         .mhomed         = True,
8211                         .num_ips        = ctx->addresses_mhomed_num,
8212                         .ips            = ctx->addresses_mhomed,
8213                         .apply_expected = True
8214                 },
8215                 .defend = {
8216                         .timeout        = 10,
8217                         .positive       = True
8218                 },
8219                 .replica= {
8220                         .type           = WREPL_TYPE_MHOMED,
8221                         .state          = WREPL_STATE_ACTIVE,
8222                         .node           = WREPL_NODE_B,
8223                         .is_static      = False,
8224                         .num_ips        = ctx->addresses_best_num,
8225                         .ips            = ctx->addresses_best,
8226                         .mhomed_merge   = True
8227                 },
8228         },
8229         /*
8230          * mhomed,active vs. mhomed,active with subset ip(s), positive response, with all addresses
8231          */
8232         {
8233                 .line   = __location__,
8234                 .name   = _NBT_NAME("_MA_MA_SB_A", 0x00, NULL),
8235                 .skip   = (ctx->addresses_all_num < 3),
8236                 .wins   = {
8237                         .nb_flags       = 0,
8238                         .mhomed         = True,
8239                         .num_ips        = ctx->addresses_mhomed_num,
8240                         .ips            = ctx->addresses_mhomed,
8241                         .apply_expected = True
8242                 },
8243                 .defend = {
8244                         .timeout        = 10,
8245                         .positive       = True,
8246                         .num_ips        = ctx->addresses_all_num,
8247                         .ips            = ctx->addresses_all,
8248                 },
8249                 .replica= {
8250                         .type           = WREPL_TYPE_MHOMED,
8251                         .state          = WREPL_STATE_ACTIVE,
8252                         .node           = WREPL_NODE_B,
8253                         .is_static      = False,
8254                         .num_ips        = ctx->addresses_best_num,
8255                         .ips            = ctx->addresses_best,
8256                         .mhomed_merge   = True
8257                 },
8258         },
8259         /*
8260          * mhomed,active vs. mhomed,active with subset ip(s), positive response, with replicas addresses
8261          * TODO: check why the server sends a name release demand for one address?
8262          *       the release demand has no effect to the database record...
8263          */
8264         {
8265                 .line   = __location__,
8266                 .name   = _NBT_NAME("_MA_MA_SB_C", 0x00, NULL),
8267                 .skip   = (ctx->addresses_all_num < 3),
8268                 .wins   = {
8269                         .nb_flags       = 0,
8270                         .mhomed         = True,
8271                         .num_ips        = ctx->addresses_mhomed_num,
8272                         .ips            = ctx->addresses_mhomed,
8273                         .apply_expected = True
8274                 },
8275                 .defend = {
8276                         .timeout        = 10,
8277                         .positive       = True,
8278                         .num_ips        = ctx->addresses_best_num,
8279                         .ips            = ctx->addresses_best,
8280                         .late_release   = True
8281                 },
8282                 .replica= {
8283                         .type           = WREPL_TYPE_MHOMED,
8284                         .state          = WREPL_STATE_ACTIVE,
8285                         .node           = WREPL_NODE_B,
8286                         .is_static      = False,
8287                         .num_ips        = ctx->addresses_best_num,
8288                         .ips            = ctx->addresses_best,
8289                         .apply_expected = False
8290                 },
8291         },
8292         /*
8293          * mhomed,active vs. mhomed,active with subset ip(s), positive response, with other addresses
8294          */
8295         {
8296                 .line   = __location__,
8297                 .name   = _NBT_NAME("_MA_MA_SB_O", 0x00, NULL),
8298
8299                 .skip   = (ctx->addresses_all_num < 3),
8300                 .wins   = {
8301                         .nb_flags       = 0,
8302                         .mhomed         = True,
8303                         .num_ips        = ctx->addresses_mhomed_num,
8304                         .ips            = ctx->addresses_mhomed,
8305                         .apply_expected = True
8306                 },
8307                 .defend = {
8308                         .timeout        = 10,
8309                         .positive       = True,
8310                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
8311                         .ips            = addresses_B_3_4,
8312                 },
8313                 .replica= {
8314                         .type           = WREPL_TYPE_MHOMED,
8315                         .state          = WREPL_STATE_ACTIVE,
8316                         .node           = WREPL_NODE_B,
8317                         .is_static      = False,
8318                         .num_ips        = ctx->addresses_best_num,
8319                         .ips            = ctx->addresses_best,
8320                         .apply_expected = False
8321                 },
8322         },
8323         /*
8324          * mhomed,active vs. mhomed,active with subset ip(s), negative response
8325          */
8326         {
8327                 .line   = __location__,
8328                 .name   = _NBT_NAME("_MA_MA_SB_N", 0x00, NULL),
8329                 .skip   = (ctx->addresses_mhomed_num != 2),
8330                 .wins   = {
8331                         .nb_flags       = 0,
8332                         .mhomed         = True,
8333                         .num_ips        = ctx->addresses_mhomed_num,
8334                         .ips            = ctx->addresses_mhomed,
8335                         .apply_expected = True
8336                 },
8337                 .defend = {
8338                         .timeout        = 10,
8339                         .positive       = False
8340                 },
8341                 .replica= {
8342                         .type           = WREPL_TYPE_MHOMED,
8343                         .state          = WREPL_STATE_ACTIVE,
8344                         .node           = WREPL_NODE_B,
8345                         .is_static      = False,
8346                         .num_ips        = ctx->addresses_best_num,
8347                         .ips            = ctx->addresses_best,
8348                         .apply_expected = True
8349                 },
8350         },
8351 /*
8352  * some more multi homed and unique test, including merging
8353  */
8354         /*
8355          * mhomed,active vs. unique,active with subset ip(s), positive response
8356          */
8357         {
8358                 .line   = __location__,
8359                 .section= "Test Replica vs. owned active: some more UNIQUE,MHOMED combinations",
8360                 .name   = _NBT_NAME("_MA_UA_SB_A", 0x00, NULL),
8361                 .skip   = (ctx->addresses_all_num < 3),
8362                 .wins   = {
8363                         .nb_flags       = 0,
8364                         .mhomed         = True,
8365                         .num_ips        = ctx->addresses_mhomed_num,
8366                         .ips            = ctx->addresses_mhomed,
8367                         .apply_expected = True
8368                 },
8369                 .defend = {
8370                         .timeout        = 10,
8371                         .positive       = True,
8372                 },
8373                 .replica= {
8374                         .type           = WREPL_TYPE_UNIQUE,
8375                         .state          = WREPL_STATE_ACTIVE,
8376                         .node           = WREPL_NODE_B,
8377                         .is_static      = False,
8378                         .num_ips        = ctx->addresses_best_num,
8379                         .ips            = ctx->addresses_best,
8380                         .mhomed_merge   = True
8381                 },
8382         },
8383         /*
8384          * unique,active vs. unique,active with different ip(s), positive response, with all addresses
8385          */
8386         {
8387                 .line   = __location__,
8388                 .name   = _NBT_NAME("_UA_UA_DI_A", 0x00, NULL),
8389                 .skip   = (ctx->addresses_all_num < 3),
8390                 .wins   = {
8391                         .nb_flags       = 0,
8392                         .mhomed         = False,
8393                         .num_ips        = ctx->addresses_best_num,
8394                         .ips            = ctx->addresses_best,
8395                         .apply_expected = True
8396                 },
8397                 .defend = {
8398                         .timeout        = 10,
8399                         .positive       = True,
8400                         .num_ips        = ctx->addresses_all_num,
8401                         .ips            = ctx->addresses_all,
8402                 },
8403                 .replica= {
8404                         .type           = WREPL_TYPE_UNIQUE,
8405                         .state          = WREPL_STATE_ACTIVE,
8406                         .node           = WREPL_NODE_B,
8407                         .is_static      = False,
8408                         .num_ips        = ctx->addresses_best2_num,
8409                         .ips            = ctx->addresses_best2,
8410                         .mhomed_merge   = True,
8411                 },
8412         },
8413         /*
8414          * unique,active vs. mhomed,active with different ip(s), positive response, with all addresses
8415          */
8416         {
8417                 .line   = __location__,
8418                 .name   = _NBT_NAME("_UA_MA_DI_A", 0x00, NULL),
8419                 .skip   = (ctx->addresses_all_num < 3),
8420                 .wins   = {
8421                         .nb_flags       = 0,
8422                         .mhomed         = False,
8423                         .num_ips        = ctx->addresses_best_num,
8424                         .ips            = ctx->addresses_best,
8425                         .apply_expected = True
8426                 },
8427                 .defend = {
8428                         .timeout        = 10,
8429                         .positive       = True,
8430                         .num_ips        = ctx->addresses_all_num,
8431                         .ips            = ctx->addresses_all,
8432                 },
8433                 .replica= {
8434                         .type           = WREPL_TYPE_MHOMED,
8435                         .state          = WREPL_STATE_ACTIVE,
8436                         .node           = WREPL_NODE_B,
8437                         .is_static      = False,
8438                         .num_ips        = ctx->addresses_best2_num,
8439                         .ips            = ctx->addresses_best2,
8440                         .mhomed_merge   = True,
8441                 },
8442         },
8443 /*
8444  * special group vs. special group merging section
8445  */
8446         /*
8447          * sgroup,active vs. sgroup,active with different ip(s)
8448          */
8449         {
8450                 .line   = __location__,
8451                 .section= "Test Replica vs. owned active: SGROUP vs. SGROUP tests",
8452                 .name   = _NBT_NAME("_SA_SA_DI_U", 0x1C, NULL),
8453                 .skip   = (ctx->addresses_all_num < 3),
8454                 .wins   = {
8455                         .nb_flags       = NBT_NM_GROUP,
8456                         .mhomed         = False,
8457                         .num_ips        = ctx->addresses_mhomed_num,
8458                         .ips            = ctx->addresses_mhomed,
8459                         .apply_expected = True
8460                 },
8461                 .defend = {
8462                         .timeout        = 0,
8463                 },
8464                 .replica= {
8465                         .type           = WREPL_TYPE_SGROUP,
8466                         .state          = WREPL_STATE_ACTIVE,
8467                         .node           = WREPL_NODE_B,
8468                         .is_static      = False,
8469                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
8470                         .ips            = addresses_B_3_4,
8471                         .sgroup_merge   = True
8472                 },
8473         },
8474         /*
8475          * sgroup,active vs. sgroup,active with same ip(s)
8476          */
8477         {
8478                 .line   = __location__,
8479                 .name   = _NBT_NAME("_SA_SA_SI_U", 0x1C, NULL),
8480                 .skip   = (ctx->addresses_all_num < 3),
8481                 .wins   = {
8482                         .nb_flags       = NBT_NM_GROUP,
8483                         .mhomed         = False,
8484                         .num_ips        = ctx->addresses_mhomed_num,
8485                         .ips            = ctx->addresses_mhomed,
8486                         .apply_expected = True
8487                 },
8488                 .defend = {
8489                         .timeout        = 0,
8490                 },
8491                 .replica= {
8492                         .type           = WREPL_TYPE_SGROUP,
8493                         .state          = WREPL_STATE_ACTIVE,
8494                         .node           = WREPL_NODE_B,
8495                         .is_static      = False,
8496                         .num_ips        = ctx->addresses_mhomed_num,
8497                         .ips            = ctx->addresses_mhomed,
8498                         .sgroup_merge   = True
8499                 },
8500         },
8501         /*
8502          * sgroup,active vs. sgroup,active with superset ip(s)
8503          */
8504         {
8505                 .line   = __location__,
8506                 .name   = _NBT_NAME("_SA_SA_SP_U", 0x1C, NULL),
8507                 .skip   = (ctx->addresses_all_num < 3),
8508                 .wins   = {
8509                         .nb_flags       = NBT_NM_GROUP,
8510                         .mhomed         = False,
8511                         .num_ips        = ctx->addresses_mhomed_num,
8512                         .ips            = ctx->addresses_mhomed,
8513                         .apply_expected = True
8514                 },
8515                 .defend = {
8516                         .timeout        = 0,
8517                 },
8518                 .replica= {
8519                         .type           = WREPL_TYPE_SGROUP,
8520                         .state          = WREPL_STATE_ACTIVE,
8521                         .node           = WREPL_NODE_B,
8522                         .is_static      = False,
8523                         .num_ips        = ctx->addresses_all_num,
8524                         .ips            = ctx->addresses_all,
8525                         .sgroup_merge   = True
8526                 },
8527         },
8528         /*
8529          * sgroup,active vs. sgroup,active with subset ip(s)
8530          */
8531         {
8532                 .line   = __location__,
8533                 .name   = _NBT_NAME("_SA_SA_SB_U", 0x1C, NULL),
8534                 .skip   = (ctx->addresses_all_num < 3),
8535                 .wins   = {
8536                         .nb_flags       = NBT_NM_GROUP,
8537                         .mhomed         = False,
8538                         .num_ips        = ctx->addresses_mhomed_num,
8539                         .ips            = ctx->addresses_mhomed,
8540                         .apply_expected = True
8541                 },
8542                 .defend = {
8543                         .timeout        = 0,
8544                 },
8545                 .replica= {
8546                         .type           = WREPL_TYPE_SGROUP,
8547                         .state          = WREPL_STATE_ACTIVE,
8548                         .node           = WREPL_NODE_B,
8549                         .is_static      = False,
8550                         .num_ips        = ctx->addresses_best_num,
8551                         .ips            = ctx->addresses_best,
8552                         .sgroup_merge   = True
8553                 },
8554         },
8555         /*
8556          * sgroup,active vs. sgroup,tombstone with different ip(s)
8557          */
8558         {
8559                 .line   = __location__,
8560                 .name   = _NBT_NAME("_SA_ST_DI_U", 0x1C, NULL),
8561                 .skip   = (ctx->addresses_all_num < 3),
8562                 .wins   = {
8563                         .nb_flags       = NBT_NM_GROUP,
8564                         .mhomed         = False,
8565                         .num_ips        = ctx->addresses_mhomed_num,
8566                         .ips            = ctx->addresses_mhomed,
8567                         .apply_expected = True
8568                 },
8569                 .defend = {
8570                         .timeout        = 0,
8571                 },
8572                 .replica= {
8573                         .type           = WREPL_TYPE_SGROUP,
8574                         .state          = WREPL_STATE_TOMBSTONE,
8575                         .node           = WREPL_NODE_B,
8576                         .is_static      = False,
8577                         .num_ips        = ARRAY_SIZE(addresses_B_3_4),
8578                         .ips            = addresses_B_3_4,
8579                         .apply_expected = False
8580                 },
8581         },
8582         /*
8583          * sgroup,active vs. sgroup,tombstone with same ip(s)
8584          */
8585         {
8586                 .line   = __location__,
8587                 .name   = _NBT_NAME("_SA_ST_SI_U", 0x1C, NULL),
8588                 .skip   = (ctx->addresses_all_num < 3),
8589                 .wins   = {
8590                         .nb_flags       = NBT_NM_GROUP,
8591                         .mhomed         = False,
8592                         .num_ips        = ctx->addresses_mhomed_num,
8593                         .ips            = ctx->addresses_mhomed,
8594                         .apply_expected = True
8595                 },
8596                 .defend = {
8597                         .timeout        = 0,
8598                 },
8599                 .replica= {
8600                         .type           = WREPL_TYPE_SGROUP,
8601                         .state          = WREPL_STATE_TOMBSTONE,
8602                         .node           = WREPL_NODE_B,
8603                         .is_static      = False,
8604                         .num_ips        = ctx->addresses_mhomed_num,
8605                         .ips            = ctx->addresses_mhomed,
8606                         .apply_expected = False
8607                 },
8608         },
8609         /*
8610          * sgroup,active vs. sgroup,tombstone with superset ip(s)
8611          */
8612         {
8613                 .line   = __location__,
8614                 .name   = _NBT_NAME("_SA_ST_SP_U", 0x1C, NULL),
8615                 .skip   = (ctx->addresses_all_num < 3),
8616                 .wins   = {
8617                         .nb_flags       = NBT_NM_GROUP,
8618                         .mhomed         = False,
8619                         .num_ips        = ctx->addresses_mhomed_num,
8620                         .ips            = ctx->addresses_mhomed,
8621                         .apply_expected = True
8622                 },
8623                 .defend = {
8624                         .timeout        = 0,
8625                 },
8626                 .replica= {
8627                         .type           = WREPL_TYPE_SGROUP,
8628                         .state          = WREPL_STATE_TOMBSTONE,
8629                         .node           = WREPL_NODE_B,
8630                         .is_static      = False,
8631                         .num_ips        = ctx->addresses_all_num,
8632                         .ips            = ctx->addresses_all,
8633                         .apply_expected = False
8634                 },
8635         },
8636         /*
8637          * sgroup,active vs. sgroup,tombstone with subset ip(s)
8638          */
8639         {
8640                 .line   = __location__,
8641                 .name   = _NBT_NAME("_SA_ST_SB_U", 0x1C, NULL),
8642                 .skip   = (ctx->addresses_all_num < 3),
8643                 .wins   = {
8644                         .nb_flags       = NBT_NM_GROUP,
8645                         .mhomed         = False,
8646                         .num_ips        = ctx->addresses_mhomed_num,
8647                         .ips            = ctx->addresses_mhomed,
8648                         .apply_expected = True
8649                 },
8650                 .defend = {
8651                         .timeout        = 0,
8652                 },
8653                 .replica= {
8654                         .type           = WREPL_TYPE_SGROUP,
8655                         .state          = WREPL_STATE_TOMBSTONE,
8656                         .node           = WREPL_NODE_B,
8657                         .is_static      = False,
8658                         .num_ips        = ctx->addresses_best_num,
8659                         .ips            = ctx->addresses_best,
8660                         .apply_expected = False
8661                 },
8662         },
8663         };
8664
8665         if (!ctx) return False;
8666
8667         if (!ctx->nbtsock_srv) {
8668                 printf("SKIP: Test Replica records vs. owned active records: not bound to port[%d]\n",
8669                         lp_nbt_port());
8670                 return True;
8671         }
8672
8673         printf("Test Replica records vs. owned active records\n");
8674
8675         for(i=0; ret && i < ARRAY_SIZE(records); i++) {
8676                 struct timeval end;
8677                 struct test_conflict_owned_active_vs_replica_struct record = records[i];
8678                 uint32_t j, count = 1;
8679                 const char *action;
8680
8681                 if (records[i].wins.mhomed || records[i].name.type == 0x1C) {
8682                         count = records[i].wins.num_ips;
8683                 }
8684
8685                 if (records[i].section) {
8686                         printf("%s\n", records[i].section);
8687                 }
8688
8689                 if (records[i].skip) {
8690                         printf("%s => SKIPPED\n", nbt_name_string(ctx, &records[i].name));
8691                         continue;
8692                 }
8693
8694                 if (records[i].replica.mhomed_merge) {
8695                         action = "MHOMED_MERGE";
8696                 } else if (records[i].replica.sgroup_merge) {
8697                         action = "SGROUP_MERGE";
8698                 } else if (records[i].replica.apply_expected) {
8699                         action = "REPLACE";
8700                 } else {
8701                         action = "NOT REPLACE";
8702                 }
8703
8704                 printf("%s => %s\n", nbt_name_string(ctx, &records[i].name), action);
8705
8706                 /* Prepare for multi homed registration */
8707                 ZERO_STRUCT(records[i].defend);
8708                 records[i].defend.timeout       = 10;
8709                 records[i].defend.positive      = True;
8710                 nbt_set_incoming_handler(ctx->nbtsock_srv,
8711                                          test_conflict_owned_active_vs_replica_handler,
8712                                          &records[i]);
8713                 if (ctx->nbtsock_srv2) {
8714                         nbt_set_incoming_handler(ctx->nbtsock_srv2,
8715                                                  test_conflict_owned_active_vs_replica_handler,
8716                                                  &records[i]);
8717                 }
8718
8719                 /*
8720                  * Setup Register
8721                  */
8722                 for (j=0; j < count; j++) {
8723                         struct nbt_name_request *req;
8724
8725                         name_register->in.name          = records[i].name;
8726                         name_register->in.dest_addr     = ctx->address;
8727                         name_register->in.address       = records[i].wins.ips[j].ip;
8728                         name_register->in.nb_flags      = records[i].wins.nb_flags;
8729                         name_register->in.register_demand= False;
8730                         name_register->in.broadcast     = False;
8731                         name_register->in.multi_homed   = records[i].wins.mhomed;
8732                         name_register->in.ttl           = 300000;
8733                         name_register->in.timeout       = 70;
8734                         name_register->in.retries       = 0;
8735
8736                         req = nbt_name_register_send(ctx->nbtsock, name_register);
8737
8738                         /* push the request on the wire */
8739                         event_loop_once(ctx->nbtsock->event_ctx);
8740
8741                         /*
8742                          * if we register multiple addresses,
8743                          * the server will do name queries to see if the old addresses
8744                          * are still alive
8745                          */
8746                         if (records[i].wins.mhomed && j > 0) {
8747                                 end = timeval_current_ofs(records[i].defend.timeout,0);
8748                                 records[i].defend.ret = True;
8749                                 while (records[i].defend.timeout > 0) {
8750                                         event_loop_once(ctx->nbtsock_srv->event_ctx);
8751                                         if (timeval_expired(&end)) break;
8752                                 }
8753                                 ret &= records[i].defend.ret;
8754                         }
8755
8756                         status = nbt_name_register_recv(req, ctx, name_register);
8757                         if (NT_STATUS_EQUAL(status, NT_STATUS_IO_TIMEOUT)) {
8758                                 printf("No response from %s for name register\n", ctx->address);
8759                                 ret = False;
8760                         }
8761                         if (!NT_STATUS_IS_OK(status)) {
8762                                 printf("Bad response from %s for name register - %s\n",
8763                                        ctx->address, nt_errstr(status));
8764                                 ret = False;
8765                         }
8766                         CHECK_VALUE(name_register->out.rcode, 0);
8767                         CHECK_VALUE_STRING(name_register->out.reply_from, ctx->address);
8768                         CHECK_VALUE(name_register->out.name.type, records[i].name.type);
8769                         CHECK_VALUE_STRING(name_register->out.name.name, records[i].name.name);
8770                         CHECK_VALUE_STRING(name_register->out.name.scope, records[i].name.scope);
8771                         CHECK_VALUE_STRING(name_register->out.reply_addr, records[i].wins.ips[j].ip);
8772                 }
8773
8774                 /* Prepare for the current test */
8775                 records[i].defend = record.defend;
8776                 nbt_set_incoming_handler(ctx->nbtsock_srv,
8777                                          test_conflict_owned_active_vs_replica_handler,
8778                                          &records[i]);
8779                 if (ctx->nbtsock_srv2) {
8780                         nbt_set_incoming_handler(ctx->nbtsock_srv2,
8781                                                  test_conflict_owned_active_vs_replica_handler,
8782                                                  &records[i]);
8783                 }
8784
8785                 /*
8786                  * Setup Replica
8787                  */
8788                 wins_name->name         = &records[i].name;
8789                 wins_name->flags        = WREPL_NAME_FLAGS(records[i].replica.type,
8790                                                            records[i].replica.state,
8791                                                            records[i].replica.node,
8792                                                            records[i].replica.is_static);
8793                 wins_name->id           = ++ctx->b.max_version;
8794                 if (wins_name->flags & 2) {
8795                         wins_name->addresses.addresses.num_ips = records[i].replica.num_ips;
8796                         wins_name->addresses.addresses.ips     = discard_const(records[i].replica.ips);
8797                 } else {
8798                         wins_name->addresses.ip = records[i].replica.ips[0].ip;
8799                 }
8800                 wins_name->unknown      = "255.255.255.255";
8801
8802                 ret &= test_wrepl_update_one(ctx, &ctx->b, wins_name);
8803
8804                 /*
8805                  * wait for the name query, which is handled in
8806                  * test_conflict_owned_active_vs_replica_handler()
8807                  */
8808                 end = timeval_current_ofs(records[i].defend.timeout,0);
8809                 records[i].defend.ret = True;
8810                 while (records[i].defend.timeout > 0) {
8811                         event_loop_once(ctx->nbtsock_srv->event_ctx);
8812                         if (timeval_expired(&end)) break;
8813                 }
8814                 ret &= records[i].defend.ret;
8815
8816                 if (records[i].defend.late_release) {
8817                         records[i].defend = record.defend;
8818                         records[i].defend.expect_release = True;
8819                         /*
8820                          * wait for the name release demand, which is handled in
8821                          * test_conflict_owned_active_vs_replica_handler()
8822                          */
8823                         end = timeval_current_ofs(records[i].defend.timeout,0);
8824                         records[i].defend.ret = True;
8825                         while (records[i].defend.timeout > 0) {
8826                                 event_loop_once(ctx->nbtsock_srv->event_ctx);
8827                                 if (timeval_expired(&end)) break;
8828                         }
8829                         ret &= records[i].defend.ret;
8830                 }
8831
8832                 if (records[i].replica.mhomed_merge) {
8833                         ret &= test_wrepl_mhomed_merged(ctx, &ctx->c,
8834                                                         records[i].wins.num_ips, records[i].wins.ips,
8835                                                         &ctx->b,
8836                                                         records[i].replica.num_ips, records[i].replica.ips,
8837                                                         wins_name);
8838                 } else if (records[i].replica.sgroup_merge) {
8839                         ret &= test_wrepl_sgroup_merged(ctx, NULL,
8840                                                         &ctx->c,
8841                                                         records[i].wins.num_ips, records[i].wins.ips,
8842                                                         &ctx->b,
8843                                                         records[i].replica.num_ips, records[i].replica.ips,
8844                                                         wins_name);
8845                 } else {
8846                         ret &= test_wrepl_is_applied(ctx, &ctx->b, wins_name,
8847                                                      records[i].replica.apply_expected);
8848                 }
8849
8850                 if (records[i].replica.apply_expected ||
8851                     records[i].replica.mhomed_merge) {
8852                         wins_name->name         = &records[i].name;
8853                         wins_name->flags        = WREPL_NAME_FLAGS(WREPL_TYPE_UNIQUE,
8854                                                                    WREPL_STATE_TOMBSTONE,
8855                                                                    WREPL_NODE_B, False);
8856                         wins_name->id           = ++ctx->b.max_version;
8857                         wins_name->addresses.ip = addresses_B_1[0].ip;
8858                         wins_name->unknown      = "255.255.255.255";
8859
8860                         ret &= test_wrepl_update_one(ctx, &ctx->b, wins_name);
8861                         ret &= test_wrepl_is_applied(ctx, &ctx->b, wins_name, True);
8862                 } else {
8863                         for (j=0; j < count; j++) {
8864                                 struct nbt_name_socket *nbtsock = ctx->nbtsock;
8865
8866                                 if (ctx->myaddr2 && strcmp(records[i].wins.ips[j].ip, ctx->myaddr2) == 0) {
8867                                         nbtsock = ctx->nbtsock2;
8868                                 }
8869
8870                                 release->in.name        = records[i].name;
8871                                 release->in.dest_addr   = ctx->address;
8872                                 release->in.address     = records[i].wins.ips[j].ip;
8873                                 release->in.nb_flags    = records[i].wins.nb_flags;
8874                                 release->in.broadcast   = False;
8875                                 release->in.timeout     = 30;
8876                                 release->in.retries     = 0;
8877
8878                                 status = nbt_name_release(nbtsock, ctx, release);
8879                                 if (NT_STATUS_EQUAL(status, NT_STATUS_IO_TIMEOUT)) {
8880                                         printf("No response from %s for name release\n", ctx->address);
8881                                         return False;
8882                                 }
8883                                 if (!NT_STATUS_IS_OK(status)) {
8884                                         printf("Bad response from %s for name query - %s\n",
8885                                                ctx->address, nt_errstr(status));
8886                                         return False;
8887                                 }
8888                                 CHECK_VALUE(release->out.rcode, 0);
8889                         }
8890
8891                         if (records[i].replica.sgroup_merge) {
8892                                 /* clean up the SGROUP record */
8893                                 wins_name->name         = &records[i].name;
8894                                 wins_name->flags        = WREPL_NAME_FLAGS(WREPL_TYPE_SGROUP,
8895                                                                            WREPL_STATE_ACTIVE,
8896                                                                            WREPL_NODE_B, False);
8897                                 wins_name->id           = ++ctx->b.max_version;
8898                                 wins_name->addresses.addresses.num_ips = 0;
8899                                 wins_name->addresses.addresses.ips     = NULL;
8900                                 wins_name->unknown      = "255.255.255.255";
8901                                 ret &= test_wrepl_update_one(ctx, &ctx->b, wins_name);
8902
8903                                 /* take ownership of the SGROUP record */
8904                                 wins_name->name         = &records[i].name;
8905                                 wins_name->flags        = WREPL_NAME_FLAGS(WREPL_TYPE_SGROUP,
8906                                                                            WREPL_STATE_ACTIVE,
8907                                                                            WREPL_NODE_B, False);
8908                                 wins_name->id           = ++ctx->b.max_version;
8909                                 wins_name->addresses.addresses.num_ips = ARRAY_SIZE(addresses_B_1);
8910                                 wins_name->addresses.addresses.ips     = discard_const(addresses_B_1);
8911                                 wins_name->unknown      = "255.255.255.255";
8912                                 ret &= test_wrepl_update_one(ctx, &ctx->b, wins_name);
8913                                 ret &= test_wrepl_is_applied(ctx, &ctx->b, wins_name, True);
8914
8915                                 /* overwrite the SGROUP record with unique,tombstone */
8916                                 wins_name->name         = &records[i].name;
8917                                 wins_name->flags        = WREPL_NAME_FLAGS(WREPL_TYPE_UNIQUE,
8918                                                                            WREPL_STATE_TOMBSTONE,
8919                                                                            WREPL_NODE_B, False);
8920                                 wins_name->id           = ++ctx->b.max_version;
8921                                 wins_name->addresses.ip = addresses_A_1[0].ip;
8922                                 wins_name->unknown      = "255.255.255.255";
8923                                 ret &= test_wrepl_update_one(ctx, &ctx->b, wins_name);
8924                                 ret &= test_wrepl_is_applied(ctx, &ctx->b, wins_name, True);
8925                         }
8926                 }
8927
8928 done:
8929                 if (!ret) {
8930                         printf("conflict handled wrong or record[%u]: %s\n", i, records[i].line);
8931                         return ret;
8932                 }
8933         }
8934
8935         return ret;
8936 }
8937
8938 #define _NBT_ASSERT(v, correct) do { \
8939         if ((v) != (correct)) { \
8940                 printf("(%s) Incorrect value %s=%d - should be %s (%d)\n", \
8941                        __location__, #v, v, #correct, correct); \
8942                 return; \
8943         } \
8944 } while (0)
8945
8946 #define _NBT_ASSERT_STRING(v, correct) do { \
8947         if ( ((!v) && (correct)) || \
8948              ((v) && (!correct)) || \
8949              ((v) && (correct) && strcmp(v,correct) != 0)) { \
8950                 printf("(%s) Incorrect value %s=%s - should be %s\n", \
8951                        __location__, #v, v, correct); \
8952                 return; \
8953         } \
8954 } while (0)
8955
8956 static void test_conflict_owned_active_vs_replica_handler_query(struct nbt_name_socket *nbtsock, 
8957                                                                 struct nbt_name_packet *req_packet, 
8958                                                                 const struct nbt_peer_socket *src)
8959 {
8960         struct nbt_name *name;
8961         struct nbt_name_packet *rep_packet;
8962         struct test_conflict_owned_active_vs_replica_struct *rec = nbtsock->incoming.private;
8963
8964         _NBT_ASSERT(req_packet->qdcount, 1);
8965         _NBT_ASSERT(req_packet->questions[0].question_type, NBT_QTYPE_NETBIOS);
8966         _NBT_ASSERT(req_packet->questions[0].question_class, NBT_QCLASS_IP);
8967
8968         name = &req_packet->questions[0].name;
8969
8970         _NBT_ASSERT(name->type, rec->name.type);
8971         _NBT_ASSERT_STRING(name->name, rec->name.name);
8972         _NBT_ASSERT_STRING(name->scope, rec->name.scope);
8973
8974         _NBT_ASSERT(rec->defend.expect_release, False);
8975
8976         rep_packet = talloc_zero(nbtsock, struct nbt_name_packet);
8977         if (rep_packet == NULL) return;
8978
8979         rep_packet->name_trn_id = req_packet->name_trn_id;
8980         rep_packet->ancount     = 1;
8981
8982         rep_packet->answers     = talloc_array(rep_packet, struct nbt_res_rec, 1);
8983         if (rep_packet->answers == NULL) return;
8984
8985         rep_packet->answers[0].name      = *name;
8986         rep_packet->answers[0].rr_class  = NBT_QCLASS_IP;
8987         rep_packet->answers[0].ttl       = 0;
8988
8989         if (rec->defend.positive) {
8990                 uint32_t i, num_ips;
8991                 const struct wrepl_ip *ips;             
8992
8993                 if (rec->defend.num_ips > 0) {
8994                         num_ips = rec->defend.num_ips;
8995                         ips     = rec->defend.ips;
8996                 } else {
8997                         num_ips = rec->wins.num_ips;
8998                         ips     = rec->wins.ips;
8999                 }
9000
9001                 /* send a positive reply */
9002                 rep_packet->operation   = 
9003                                         NBT_FLAG_REPLY | 
9004                                         NBT_OPCODE_QUERY | 
9005                                         NBT_FLAG_AUTHORITIVE |
9006                                         NBT_FLAG_RECURSION_DESIRED |
9007                                         NBT_FLAG_RECURSION_AVAIL;
9008
9009                 rep_packet->answers[0].rr_type   = NBT_QTYPE_NETBIOS;
9010
9011                 rep_packet->answers[0].rdata.netbios.length = num_ips*6;
9012                 rep_packet->answers[0].rdata.netbios.addresses = 
9013                         talloc_array(rep_packet->answers, struct nbt_rdata_address, num_ips);
9014                 if (rep_packet->answers[0].rdata.netbios.addresses == NULL) return;
9015
9016                 for (i=0; i < num_ips; i++) {
9017                         struct nbt_rdata_address *addr = 
9018                                 &rep_packet->answers[0].rdata.netbios.addresses[i];
9019                         addr->nb_flags  = rec->wins.nb_flags;
9020                         addr->ipaddr    = ips[i].ip;
9021                 }
9022                 DEBUG(2,("Sending positive name query reply for %s to %s:%d\n", 
9023                         nbt_name_string(rep_packet, name), src->addr, src->port));
9024         } else {
9025                 /* send a negative reply */
9026                 rep_packet->operation   =
9027                                         NBT_FLAG_REPLY | 
9028                                         NBT_OPCODE_QUERY | 
9029                                         NBT_FLAG_AUTHORITIVE |
9030                                         NBT_RCODE_NAM;
9031
9032                 rep_packet->answers[0].rr_type   = NBT_QTYPE_NULL;
9033
9034                 ZERO_STRUCT(rep_packet->answers[0].rdata);
9035
9036                 DEBUG(2,("Sending negative name query reply for %s to %s:%d\n", 
9037                         nbt_name_string(rep_packet, name), src->addr, src->port));
9038         }
9039
9040         nbt_name_reply_send(nbtsock, src, rep_packet);
9041         talloc_free(rep_packet);
9042
9043         /* make sure we push the reply to the wire */
9044         event_loop_once(nbtsock->event_ctx);
9045
9046         rec->defend.timeout     = 0;
9047         rec->defend.ret         = True;
9048 }
9049
9050 static void test_conflict_owned_active_vs_replica_handler_release(struct nbt_name_socket *nbtsock, 
9051                                                                   struct nbt_name_packet *req_packet, 
9052                                                                   const struct nbt_peer_socket *src)
9053 {
9054         struct nbt_name *name;
9055         struct nbt_name_packet *rep_packet;
9056         struct test_conflict_owned_active_vs_replica_struct *rec = nbtsock->incoming.private;
9057
9058         _NBT_ASSERT(req_packet->qdcount, 1);
9059         _NBT_ASSERT(req_packet->questions[0].question_type, NBT_QTYPE_NETBIOS);
9060         _NBT_ASSERT(req_packet->questions[0].question_class, NBT_QCLASS_IP);
9061
9062         name = &req_packet->questions[0].name;
9063
9064         _NBT_ASSERT(name->type, rec->name.type);
9065         _NBT_ASSERT_STRING(name->name, rec->name.name);
9066         _NBT_ASSERT_STRING(name->scope, rec->name.scope);
9067
9068         _NBT_ASSERT(rec->defend.expect_release, True);
9069
9070         rep_packet = talloc_zero(nbtsock, struct nbt_name_packet);
9071         if (rep_packet == NULL) return;
9072
9073         rep_packet->name_trn_id = req_packet->name_trn_id;
9074         rep_packet->ancount     = 1;
9075         rep_packet->operation   = 
9076                                 NBT_FLAG_REPLY | 
9077                                 NBT_OPCODE_RELEASE |
9078                                 NBT_FLAG_AUTHORITIVE;
9079
9080         rep_packet->answers     = talloc_array(rep_packet, struct nbt_res_rec, 1);
9081         if (rep_packet->answers == NULL) return;
9082
9083         rep_packet->answers[0].name     = *name;
9084         rep_packet->answers[0].rr_type  = NBT_QTYPE_NETBIOS;
9085         rep_packet->answers[0].rr_class = NBT_QCLASS_IP;
9086         rep_packet->answers[0].ttl      = req_packet->additional[0].ttl;
9087         rep_packet->answers[0].rdata    = req_packet->additional[0].rdata;
9088
9089         DEBUG(2,("Sending name release reply for %s to %s:%d\n", 
9090                 nbt_name_string(rep_packet, name), src->addr, src->port));
9091
9092         nbt_name_reply_send(nbtsock, src, rep_packet);
9093         talloc_free(rep_packet);
9094
9095         /* make sure we push the reply to the wire */
9096         event_loop_once(nbtsock->event_ctx);
9097
9098         rec->defend.timeout     = 0;
9099         rec->defend.ret         = True;
9100 }
9101
9102 static void test_conflict_owned_active_vs_replica_handler(struct nbt_name_socket *nbtsock, 
9103                                                           struct nbt_name_packet *req_packet, 
9104                                                           const struct nbt_peer_socket *src)
9105 {
9106         struct test_conflict_owned_active_vs_replica_struct *rec = nbtsock->incoming.private;
9107
9108         rec->defend.ret = False;
9109
9110         switch (req_packet->operation & NBT_OPCODE) {
9111         case NBT_OPCODE_QUERY:
9112                 test_conflict_owned_active_vs_replica_handler_query(nbtsock, req_packet, src);
9113                 break;
9114         case NBT_OPCODE_RELEASE:
9115                 test_conflict_owned_active_vs_replica_handler_release(nbtsock, req_packet, src);
9116                 break;
9117         default:
9118                 printf("%s: unexpected incoming packet\n", __location__);
9119                 return;
9120         }
9121 }
9122
9123 /*
9124   test WINS replication operations
9125 */
9126 BOOL torture_nbt_winsreplication_quick(void)
9127 {
9128         const char *address;
9129         struct nbt_name name;
9130         TALLOC_CTX *mem_ctx = talloc_new(NULL);
9131         NTSTATUS status;
9132         BOOL ret = True;
9133
9134         make_nbt_name_server(&name, lp_parm_string(-1, "torture", "host"));
9135
9136         /* do an initial name resolution to find its IP */
9137         status = resolve_name(&name, mem_ctx, &address, NULL);
9138         if (!NT_STATUS_IS_OK(status)) {
9139                 printf("Failed to resolve %s - %s\n",
9140                        name.name, nt_errstr(status));
9141                 talloc_free(mem_ctx);
9142                 return False;
9143         }
9144
9145         ret &= test_assoc_ctx1(mem_ctx, address);
9146         ret &= test_assoc_ctx2(mem_ctx, address);
9147
9148         ret &= test_wins_replication(mem_ctx, address);
9149
9150         talloc_free(mem_ctx);
9151
9152         return ret;
9153 }
9154
9155 /*
9156   test WINS replication operations
9157 */
9158 BOOL torture_nbt_winsreplication(void)
9159 {
9160         const char *address;
9161         struct nbt_name name;
9162         TALLOC_CTX *mem_ctx = talloc_new(NULL);
9163         NTSTATUS status;
9164         BOOL ret = True;
9165         struct test_wrepl_conflict_conn *ctx;
9166
9167         make_nbt_name_server(&name, lp_parm_string(-1, "torture", "host"));
9168
9169         /* do an initial name resolution to find its IP */
9170         status = resolve_name(&name, mem_ctx, &address, NULL);
9171         if (!NT_STATUS_IS_OK(status)) {
9172                 printf("Failed to resolve %s - %s\n",
9173                        name.name, nt_errstr(status));
9174                 talloc_free(mem_ctx);
9175                 return False;
9176         }
9177
9178         ret &= test_assoc_ctx1(mem_ctx, address);
9179         ret &= test_assoc_ctx2(mem_ctx, address);
9180
9181         ret &= test_wins_replication(mem_ctx, address);
9182
9183         ctx = test_create_conflict_ctx(mem_ctx, address);
9184
9185         ret &= test_conflict_same_owner(ctx);
9186         ret &= test_conflict_different_owner(ctx);
9187         ret &= test_conflict_owned_released_vs_replica(ctx);
9188         ret &= test_conflict_owned_active_vs_replica(ctx);
9189
9190         talloc_free(mem_ctx);
9191
9192         return ret;
9193 }