86 show_all =
"--all" in sys.argv
87 as_json =
"--json" in sys.argv
89 decls = collections.defaultdict(list)
90 defs = collections.defaultdict(list)
93 path, name, kind = tag.get(
"path",
""), tag.get(
"name",
""), tag.get(
"kind",
"")
98 if kind ==
"prototype" and path.endswith((
".h",
".hpp")):
99 decls[name].append((path, tag.get(
"line", 0)))
100 elif kind ==
"function" and path.endswith((
".c",
".cc",
".cpp")):
108 defs[name].append((path, tag.get(
"line", 0)))
114 INTERFACE_MIN_IMPLS = 3
117 for name, places
in sorted(decls.items()):
120 if len(defs[name]) >= INTERFACE_MIN_IMPLS:
122 for hdr, hline
in places:
125 if any(
module_of(p) == (hdir, hstem)
for p, _
in defs[name]):
127 for src, sline
in defs[name]:
130 if cross
or show_all:
133 "declared_in": f
"{hdr}:{hline}",
134 "defined_in": f
"{src}:{sline}",
135 "cross_module": cross,
140 print(json.dumps(findings, indent=2))
143 cross = [f
for f
in findings
if f[
"cross_module"]]
144 same = [f
for f
in findings
if not f[
"cross_module"]]
146 by_cat = collections.Counter(f[
"category"]
for f
in cross)
147 print(f
"{len(cross)} cross-directory mismatch(es)"
148 + (f
", {len(same)} same-directory" if show_all
else "")
150 for cat, n
in by_cat.most_common():
151 print(f
" {n:4d} {cat}")
157 for cat
in (SUBDIR, PARENTDIR, ORCHESTRATOR):
158 rows = [f
for f
in cross
if f[
"category"] == cat]
161 pairs = collections.Counter(
162 (f[
"declared_in"].split(
":")[0], f[
"defined_in"].split(
":")[0])
for f
in rows
164 print(f
"--- {cat} ({len(rows)}) ---")
165 for (h, s), n
in pairs.most_common():
166 print(f
" {n:3d} {h} -> {s}")
169 rows = [f
for f
in cross
if f[
"category"] == UNRELATED]
170 print(f
"--- {UNRELATED} ({len(rows)}) : the ones worth looking at ---")
171 for f
in sorted(rows, key=
lambda x: (x[
"declared_in"], x[
"symbol"])):
172 print(f
" {f['symbol']}")
173 print(f
" declared {f['declared_in']}")
174 print(f
" defined {f['defined_in']}")
176 if show_all
and same:
177 print(
"\n--- same directory, different file (often deliberate) ---")
178 for f
in sorted(same, key=
lambda x: (x[
"declared_in"], x[
"symbol"])):
179 print(f
" {f['symbol']}: {f['declared_in']} -> {f['defined_in']}")