summaryrefslogtreecommitdiff
path: root/build-aux/measurestack/analyze.py
diff options
context:
space:
mode:
Diffstat (limited to 'build-aux/measurestack/analyze.py')
-rw-r--r--build-aux/measurestack/analyze.py55
1 files changed, 32 insertions, 23 deletions
diff --git a/build-aux/measurestack/analyze.py b/build-aux/measurestack/analyze.py
index f454b7e..67c44ce 100644
--- a/build-aux/measurestack/analyze.py
+++ b/build-aux/measurestack/analyze.py
@@ -231,28 +231,39 @@ class AnalyzeResult(typing.NamedTuple):
class SkipModel(typing.NamedTuple):
"""Running the skipmodel calls `.fn(chain, ...)` with the chain
- consisting of the last `.nchain` items (if .nchain is an int), or
- the chain starting with the *last* occurance of `.nchain` in
- chain[:-1] (if .nchain is a collection). If the chain is not that
- long or does not contain a member of the collection, then .fn is
- not called and the call is *not* skipped.
+ consisting of the last few items of the input chain.
+ If `.nchain` is an int:
+
+ - the chain is the last `.nchain` items or the input chain. If
+ the input chain is not that long, then `.fn` is not called and
+ the call is *not* skipped.
+
+ If `.nchain` is a collection:
+
+ - the chain starts with the *last* occurance of `.nchain` in the
+ input chain. If the input chain does not contain a member of
+ the collection, then .fn is called with an empty chain.
"""
nchain: int | typing.Collection[BaseName]
- fn: typing.Callable[[typing.Sequence[QName], QName], bool]
-
- def __call__(self, chain: typing.Sequence[QName], call: QName) -> tuple[bool, int]:
- if isinstance(self.nchain, int):
- if len(chain) >= self.nchain:
- _chain = chain[-self.nchain :]
- return self.fn(_chain, call), len(_chain)
- else:
- for i in reversed(range(len(chain) - 1)):
- if chain[i].base() in self.nchain:
- _chain = chain[i:]
- return self.fn(_chain, call), len(_chain)
- return False, 0
+ fn: typing.Callable[[typing.Sequence[QName], Node, QName], bool]
+
+ def __call__(
+ self, chain: typing.Sequence[QName], node: Node, call: QName
+ ) -> tuple[bool, int]:
+ match self.nchain:
+ case int():
+ if len(chain) >= self.nchain:
+ _chain = chain[-self.nchain :]
+ return self.fn(_chain, node, call), len(_chain) + 1
+ return False, 0
+ case _:
+ for i in reversed(range(len(chain))):
+ if chain[i].base() in self.nchain:
+ _chain = chain[i:]
+ return self.fn(_chain, node, call), len(_chain) + 1
+ return self.fn([], node, call), 1
class Application(typing.Protocol):
@@ -458,9 +469,7 @@ def analyze(
skipmodels = app.skipmodels()
for name, model in skipmodels.items():
- if isinstance(model.nchain, int):
- assert model.nchain > 1
- else:
+ if not isinstance(model.nchain, int):
assert len(model.nchain) > 0
_nstatic_cache: dict[QName, int] = {}
@@ -495,7 +504,7 @@ def analyze(
call_qname = graphdata.resolve_funcname(call_orig_qname)
if not call_qname:
if skipmodel:
- skip, _ = skipmodel(chain, call_orig_qname)
+ skip, _ = skipmodel(chain[:-1], node, call_orig_qname)
if skip:
if dbg_nstatic:
putdbg(f"{call_orig_qname}\tskip missing")
@@ -508,7 +517,7 @@ def analyze(
# 2. Skip
if skipmodel:
- skip, skip_nchain = skipmodel(chain, call_qname)
+ skip, skip_nchain = skipmodel(chain[:-1], node, call_qname)
max_call_nchain = max(max_call_nchain, skip_nchain)
if skip:
if dbg_nstatic: