添加仓库完整性体检原始数据与扫描脚本
This commit is contained in:
@@ -0,0 +1,85 @@
|
||||
#!/usr/bin/env python3
|
||||
"""Scan cloned RISC-V repos and print a compact completeness report."""
|
||||
import os, subprocess, io, sys
|
||||
|
||||
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding="utf-8")
|
||||
REPO_DIR = "/data/repos"
|
||||
REPOS = ["serv", "neorv32", "picorv32", "ibex", "VexRiscv",
|
||||
"e203_hbirdv2", "pulpino", "pulpissimo", "opentitan"]
|
||||
|
||||
RTL_EXT = {".v", ".sv", ".svh", ".vh", ".vhd", ".vhdl", ".fhdl", ".scala"}
|
||||
TB_DIRS = {"tb", "tb_core", "testbench", "verif", "dv", "dv_uvm", "tests", "test", "tbench"}
|
||||
DOC_EXT = {".md", ".rst", ".tex", ".pdf"}
|
||||
|
||||
def head_date(repo):
|
||||
try:
|
||||
out = subprocess.run(["git", "log", "-1", "--format=%ci %h"],
|
||||
cwd=os.path.join(REPO_DIR, repo), capture_output=True, text=True).stdout
|
||||
return out.strip()[:16]
|
||||
except Exception:
|
||||
return "?"
|
||||
|
||||
def scan(repo):
|
||||
root = os.path.join(REPO_DIR, repo)
|
||||
rtl_files = rtl_lines = doc_files = tb_rtl = 0
|
||||
core_files = makefiles = pyscripts = tcl = bazel = cmake = 0
|
||||
workflows, licenses = [], []
|
||||
gitmods = []
|
||||
for dirpath, dirnames, filenames in os.walk(root):
|
||||
dirnames[:] = [d for d in dirnames if d != ".git"]
|
||||
rel = os.path.relpath(dirpath, root)
|
||||
parts = set(rel.replace("\\", "/").split("/"))
|
||||
for f in filenames:
|
||||
p = os.path.join(dirpath, f)
|
||||
ext = os.path.splitext(f)[1].lower()
|
||||
lf = f.lower()
|
||||
if ext in RTL_EXT:
|
||||
try:
|
||||
with open(p, "rb") as fh:
|
||||
n = sum(1 for _ in fh)
|
||||
except Exception:
|
||||
n = 0
|
||||
rtl_files += 1
|
||||
rtl_lines += n
|
||||
if parts & TB_DIRS:
|
||||
tb_rtl += 1
|
||||
elif ext in DOC_EXT:
|
||||
doc_files += 1
|
||||
if lf == "license" or lf.startswith("license."):
|
||||
licenses.append(os.path.relpath(p, root))
|
||||
if lf.endswith(".core"):
|
||||
core_files += 1
|
||||
if lf in ("makefile",) or lf.startswith("makefile.") or lf.endswith(".mk"):
|
||||
makefiles += 1
|
||||
if ext == ".py":
|
||||
pyscripts += 1
|
||||
if ext == ".tcl":
|
||||
tcl += 1
|
||||
if lf.startswith("bazelrc") or lf == "build" or lf.endswith(".bzl") or lf == "module_bazel":
|
||||
bazel += 1
|
||||
if lf in ("cmakelists.txt",):
|
||||
cmake += 1
|
||||
if rel == os.path.join(".github", "workflows"):
|
||||
workflows = [f for f in filenames if f.endswith((".yml", ".yaml"))]
|
||||
gm = os.path.join(root, ".gitmodules")
|
||||
if os.path.exists(gm):
|
||||
with open(gm, encoding="utf-8", errors="ignore") as fh:
|
||||
gitmods = [l.split("=", 1)[1].strip() for l in fh if l.strip().startswith("path =")]
|
||||
tops = sorted(d for d in os.listdir(root)
|
||||
if os.path.isdir(os.path.join(root, d)) and d != ".git")
|
||||
lic = licenses[0] if licenses else "MISSING"
|
||||
readme = os.path.exists(os.path.join(root, "README.md")) or os.path.exists(os.path.join(root, "README.rst"))
|
||||
print(f"=== {repo} ===")
|
||||
print(f"HEAD: {head_date(repo)} | LICENSE: {lic} | README: {'Y' if readme else 'N'}")
|
||||
print(f"RTL files: {rtl_files} | RTL lines: {rtl_lines} | TB rtl files: {tb_rtl} | doc files: {doc_files}")
|
||||
print(f"FuseSoC .core: {core_files} | Makefile: {makefiles} | .py: {pyscripts} | .tcl: {tcl} | bazel-ish: {bazel} | cmake: {cmake}")
|
||||
print(f"CI workflows: {len(workflows)} {workflows[:4]}")
|
||||
print(f"submodules({len(gitmods)}): {gitmods[:12]}")
|
||||
print(f"top dirs: {tops}")
|
||||
print()
|
||||
|
||||
for r in REPOS:
|
||||
try:
|
||||
scan(r)
|
||||
except Exception as e:
|
||||
print(f"=== {r} === ERROR {e}\n")
|
||||
Reference in New Issue
Block a user