40a41,42
>  *   -br d / -bw w structure-aware choice of the branching facet at depth <= d, window w percent (default 125)
>  *   -sym          (mode B) use the stabiliser of the root gluing: orbit-minimal options at the first branching facet
99a102
> static int adm_list_root = -1;   /* class of the root type (mode B) */
456a460,472
> }
> 
> 
> static int mulc(int a, int b);
> static int sym_on = 0, symYA = -1, nsymB = 0; static int *symB_facet = NULL, *symB_g = NULL;   /* lex-leader data (option -sym) */
> /* returns 1 if the gluing of facet B (just glued) violates the lex-leader condition for some g with g^-1 A = B */
> static int sym_check(int B) {
>     for (int k = 0; k < nsymB; k++) { if (symB_facet[k] != B) continue;
>         int g = symB_g[k]; int XB = frep[B]; int YB = sigma_pt(XB);
>         int j = pos[mulc(g, XB)]; int gy = mulc(g, YB);
>         int Yp = pt[fac[gy] * HF + hm[pos[gy] * HF + hinv[j]]];
>         if (Yp < symYA) return 1; }
>     return 0;
474a491
>     if (sym_on && (sym_check(F) || sym_check(G))) return 1;
648a666,713
> 
> 
> /* ---------------- symmetry of the root configuration (mode B, option -sym) ---------------- */
> /* a*b in the cell group: the breadth-first word of b is applied to a by right multiplications */
> static int mulc(int a, int b) {
>     int w[256], k = 0;
>     while (b != 0) { if (k >= 256) DIE("word too long"); w[k++] = cgen[b]; b = cpar[b]; }
>     while (k) a = cR[w[--k] * N + a];
>     return a;
> }
> static int use_sym = 0;
> static long long sym_removed = 0; static int sym_group = 0, sym_facet_group = 0;
> /* Mode B, depth-1 node (only the root pair F0 <-> t*H_f and what it forces is glued).
>    S = { g in C : x -> g x maps the root gluing to itself } = { g in H_f : t g = g t } u { g in t H_f : sigma(g) = g t }.
>    For g in S the relabelled pairing sigma^g(z) = g sigma(g^-1 z) is again in the same slice (root preserved, type
>    classes are invariant under left multiplication).  If g maps the branching facet A to itself, g X_A = X_A h,
>    then sigma^g(X_A) = g sigma(X_A) h^-1.  Hence every solution of the slice is conjugate to one whose value at
>    X_A is minimal in its orbit under these g; the options that are not orbit-minimal are removed.
>    For g in S that moves A (B := g^-1 A != A) the same argument gives the lex-leader condition
>        sigma(X_A) <= sigma^g(X_A) = g sigma(X_B) h^-1   (g X_B = X_A h),
>    which is tested in define_pair as soon as B is glued (sym_check): among the |S| images of a solution the one
>    with the smallest value at X_A satisfies all these conditions, so no conjugacy class is lost. */
> static int sym_filter(int F, int *opt, int cnt, int troot) {
>     int f = F % NF, XA = frep[f];
>     int *S = xmalloc(sizeof(int) * N); int nS = 0, nSA = 0;
>     int ft = fac[troot];
>     nsymB = 0;
>     for (int g = 1; g < N; g++) { if (fac[g] != 0 && fac[g] != ft) continue;
>         if (pF[fac[g]] < 0) DIE("sym: root not glued");
>         if (sigma_pt(g) != mulc(g, troot)) continue;
>         nS++;
>         if (fac[mulc(g, XA)] == f) S[nSA++] = g;
>         else { /* g does not fix the branching facet A: the gluing of B = g^-1 A will be compared with the value at A */
>             if (!symB_facet) { symB_facet = xmalloc(sizeof(int) * N); symB_g = xmalloc(sizeof(int) * N); }
>             symB_facet[nsymB] = fac[mulc(cinv[g], XA)]; symB_g[nsymB] = g; nsymB++; } }
>     sym_group = nS + 1; sym_facet_group = nSA + 1;
>     int out = 0;
>     for (int i = 0; i < cnt; i++) { int Y = opt[i], keep = 1;
>         if (Y < 0 || Y >= N) { opt[out++] = Y; continue; }
>         for (int a = 0; a < nSA && keep; a++) { int g = S[a];
>             int j = pos[mulc(g, XA)];                 /* g X_A = X_A h_j */
>             int gy = mulc(g, Y);
>             int Yp = pt[fac[gy] * HF + hm[pos[gy] * HF + hinv[j]]];   /* g Y h_j^-1 */
>             if (Yp < Y) keep = 0; }
>         if (keep) opt[out++] = Y; else sym_removed++; }
>     free(S);
>     return out;
> }
660c725
< static long long next_progress = 2000000000LL; static int top_k = 0, top_n = 0; static int deep_score = 0, deep_ref = 2, branch_rule = 0, branch_rule_depth = 1;
---
> static long long next_progress = 2000000000LL; static int top_k = 0, top_n = 0; static int deep_score = 0, deep_ref = 2, branch_rule = 0, branch_rule_depth = 1, branch_window = 125;
781c846
<             for (int i = 0; i < ncur; i++) { if (4 * cur[i].cnt > 5 * cur[b].cnt) continue;
---
>             for (int i = 0; i < ncur; i++) { if (100LL * cur[i].cnt > (long long)branch_window * cur[b].cnt) continue;
788a854
>         if (use_sym && mode == 'B' && K == 1 && depth == 1) cur[b].cnt = sym_filter(cur[b].F, cur[b].opt, cur[b].cnt, cls_min[adm_list_root]);
798a865
>             if (use_sym && mode == 'B' && K == 1 && depth == 1) { symYA = Y; sym_on = 1; }
800c867,868
<             else if (!(special && minrule)) DIE("internal error: option of a filtered domain failed");
---
>             else if (!(special && minrule) && !sym_on) DIE("internal error: option of a filtered domain failed");
>             if (use_sym && mode == 'B' && K == 1 && depth == 1) sym_on = 0;
829a898,899
>         else if (!strcmp(argv[i], "-bw")) branch_window = atoi(argv[++i]);
>         else if (!strcmp(argv[i], "-sym")) use_sym = 1;
876,877c946,947
<     printf("START %s mode=%c K=%d orient=%d N=%d M=%d NF=%d HF=%d NS=%d NVF=%d NFC=%d NR=%d classes=%d admissible=%d root_type=%d slice=%d/%d heur=%d inadm=%s restrict=%s filter=%d minrule=%d old=%d Sfresh=%d,%d fresh_depth=%d\n",
<            slice_id, mode, K, orient, N, M, NF, HF, NS, NVF, NFC, NR, ncls, nadm, root_type, slicej, sliceJ, heur, inadm_fn ? inadm_fn : "-", antipodal ? "antipodal" : "-", filt, minrule, use_old, Sfresh, Sfresh2, fresh_depth);
---
>     printf("START %s mode=%c K=%d orient=%d N=%d M=%d NF=%d HF=%d NS=%d NVF=%d NFC=%d NR=%d classes=%d admissible=%d root_type=%d slice=%d/%d heur=%d inadm=%s restrict=%s filter=%d minrule=%d old=%d Sfresh=%d,%d fresh_depth=%d br=%d,%d bw=%d sym=%d engine=v7\n",
>            slice_id, mode, K, orient, N, M, NF, HF, NS, NVF, NFC, NR, ncls, nadm, root_type, slicej, sliceJ, heur, inadm_fn ? inadm_fn : "-", antipodal ? "antipodal" : "-", filt, minrule, use_old, Sfresh, Sfresh2, fresh_depth, branch_rule, branch_rule_depth, branch_window, use_sym);
885a956
>         adm_list_root = adm_list[root_type];
913a985
>     if (use_sym) printf("SYM root-stabiliser order=%d, subgroup fixing the first branching facet=%d, options removed=%lld\n", sym_group, sym_facet_group, sym_removed);
