From 1064c994166095d611ae982de1716854493aa235 Mon Sep 17 00:00:00 2001 From: Robert Norton Date: Tue, 16 Jul 2024 17:57:47 +0100 Subject: [PATCH] perm.py: remove broken hack for excluding transitive edges Graphviz includes the tred program for computing transitive reduction so use this to post process the complete graph instead. This means that graphs containing edges that drop more than one perm that are not implied by transitivity are displayed correctly. --- archdoc/misc/perms/Makefile | 2 +- archdoc/misc/perms/perms.py | 26 ++++++++++++-------------- 2 files changed, 13 insertions(+), 15 deletions(-) diff --git a/archdoc/misc/perms/Makefile b/archdoc/misc/perms/Makefile index 9fcdac7..c20e775 100644 --- a/archdoc/misc/perms/Makefile +++ b/archdoc/misc/perms/Makefile @@ -2,7 +2,7 @@ all: perms.svg perms.dot: perms.py - ./perms.py > $@ + ./perms.py | tred > $@ %.svg : %.dot dot -Tsvg -o $@ $< diff --git a/archdoc/misc/perms/perms.py b/archdoc/misc/perms/perms.py index 7ac974a..eaa4bf1 100755 --- a/archdoc/misc/perms/perms.py +++ b/archdoc/misc/perms/perms.py @@ -134,8 +134,7 @@ def comb_to_str(c): return '_'.join(cs) or "0" # Now we output a graph representation of the useful combinations in dot format. -# To make it pretty we add edges for the subset partial order, excluding edges -# implied by transitivity. +# To make it pretty we add edges for the subset partial order. print("digraph {") @@ -143,19 +142,18 @@ def comb_to_str(c): for x in useful_combinations: print(comb_to_str(x)) -# Output the edges for the subset relation. To exclude transitive edges -# we stick to pairs of combinations that differ in size by one. This -# doesn't work for all graphs but seems to be OK for us. +# Output the edges for the subset relation. This results in many redundant edges +# but fortunately graphviz provides `tred` for computing the transitive +# reduction. for x in useful_combinations: for y in useful_combinations: - if len(x) + 1 == len(y): - xs = set(x) - ys = set(y) - if xs.issubset(ys): - # find the permission in ys not in xs to use as label - diff = (ys - xs).pop() - x_str=comb_to_str(x) - y_str=comb_to_str(y) - print(f"{y_str} -> {x_str} [label=\"{diff}\", fontsize=10]") + xs = set(x) + ys = set(y) + if xs < ys: + # find the permissions in ys not in xs to use as label + diff = ys - xs + x_str=comb_to_str(x) + y_str=comb_to_str(y) + print(f"{y_str} -> {x_str} [label=\"{comb_to_str(diff)}\", fontsize=10]") print("}")