Files
cobol-java-v3/tests/test_orchestrator_db_gcov_merge.py
T

66 lines
2.8 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
r"""子程序 gcov 行号不得并入主程序 gcov 字典的回归测试。
Bug`generate_coverage_report` 用 `gcov_data.update(sub_merged)` 把子程序
(SUB*.cbl) 的 gcov 行计数并入主程序行号字典。主程序与子程序的行号都是纯
整数,直接碰撞——SUB04CHK 的第 167 行(count=0)覆盖了 SHA02MNC 主程序
第 167 行(count=25,主循环 PERFORM 已进入),导致 #10 Enter 分支被误判为
未覆盖(SHA02MNC 覆盖率从应有的水平被拉低)。
修复:子程序 gcov 按子程序名独立保存(`_sub_gcov_data`),不并入主程序
`gcov_data`。`_merge_run_dirs_gcov` 对单个程序跨 run 目录合并。
"""
import sys, os
sys.path.insert(0, os.path.abspath(os.path.join(os.path.dirname(__file__), "..")))
from pathlib import Path
from cobol_testgen.gcov import parse_cbl_gcov
from orchestrator_db import _merge_run_dirs_gcov
def _write_fake_gcov(dirpath: Path, name: str, counts: dict[int, int]):
lines = []
for ln in sorted(counts):
cnt = counts[ln]
marker = "#####" if cnt == 0 else f"{cnt}*"
lines.append(f"{marker}:{ln}: dummy source line\n")
(dirpath / f"{name}.cbl.gcov").write_text("".join(lines), encoding="utf-8")
def _fake_gcov_func(name: str, d: str):
return parse_cbl_gcov(os.path.join(d, f"{name}.cbl.gcov"))
def test_sub_gcov_line_collision_does_not_corrupt_main(tmp_path):
run_normal = tmp_path / "run_normal"; run_normal.mkdir()
run_fail = tmp_path / "run_fail"; run_fail.mkdir()
# 主程序:line 167 在 normal 场景执行 25 次(主循环进入)
_write_fake_gcov(run_normal, "MAIN", {167: 25, 265: 1})
_write_fake_gcov(run_fail, "MAIN", {167: 0, 265: 1})
# 子程序:line 167 从未执行(count=0)——与主程序行号碰撞
_write_fake_gcov(run_normal, "SUB", {167: 0, 10: 1})
_write_fake_gcov(run_fail, "SUB", {167: 0, 10: 1})
main = _merge_run_dirs_gcov(tmp_path, "MAIN", gcov_func=_fake_gcov_func)
sub = _merge_run_dirs_gcov(tmp_path, "SUB", gcov_func=_fake_gcov_func)
# 合并后主程序 167 必须保持 25
assert main[167] == 25, f"main line 167 corrupted: {main[167]}"
assert sub[167] == 0
# 旧 bug 行为演示:若把子程序并入主程序字典,167 会被覆盖为 0
buggy = dict(main)
buggy.update(sub)
assert buggy[167] == 0, "demonstrates the corruption the fix avoids"
# 修复不变量:子程序数据独立保存,主程序字典完好
assert main[167] == 25
def test_merge_run_dirs_takes_max_count(tmp_path):
r1 = tmp_path / "run_a"; r1.mkdir()
r2 = tmp_path / "run_b"; r2.mkdir()
_write_fake_gcov(r1, "MAIN", {167: 25})
_write_fake_gcov(r2, "MAIN", {167: 3})
merged = _merge_run_dirs_gcov(tmp_path, "MAIN", gcov_func=_fake_gcov_func)
assert merged[167] == 25