forked from Classfied3D/llvm2scratch
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathdiff_compare.py
More file actions
89 lines (78 loc) · 3.06 KB
/
Copy pathdiff_compare.py
File metadata and controls
89 lines (78 loc) · 3.06 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
#!/usr/bin/env python3
import json
import sys
import zipfile
def load_project(path):
path = str(path)
if path.endswith('.sb3'):
with zipfile.ZipFile(path) as z:
for name in z.namelist():
if name.endswith('project.json'):
with z.open(name) as f:
return json.load(f)
raise ValueError(f"No project.json found in {path}")
else:
with open(path) as f:
return json.load(f)
def count_top_level_blocks(blocks, start_id):
count = 0
current_id = start_id
while current_id and current_id in blocks:
block = blocks[current_id]
if block is None:
break
opcode = block.get("opcode", "")
if opcode == "procedures_prototype":
current_id = block.get("next")
continue
count += 1
current_id = block.get("next")
return count
def get_proc_name(blocks, def_block):
cb = def_block.get("inputs", {}).get("custom_block", {})
if isinstance(cb, list) and len(cb) > 1:
proto_id = cb[1]
if isinstance(proto_id, str) and proto_id in blocks:
proto = blocks[proto_id]
if proto and proto.get("opcode") == "procedures_prototype":
return proto.get("mutation", {}).get("proccode", "unknown")
next_id = def_block.get("next")
if next_id and next_id in blocks:
nb = blocks[next_id]
if nb and nb.get("opcode") == "procedures_prototype":
return nb.get("mutation", {}).get("proccode", "unknown")
return "unknown"
def extract_procedures(targets):
procs = {}
for target in targets:
blocks = target.get("blocks", {})
for block_id, block in blocks.items():
if block is None:
continue
opcode = block.get("opcode", "")
if opcode == "procedures_definition":
proc_name = get_proc_name(blocks, block)
next_id = block.get("next")
count = count_top_level_blocks(blocks, next_id)
procs[proc_name] = count
return procs
py_path = sys.argv[1] if len(sys.argv) > 1 else "/tmp/py_sb3/Project/project.json"
rs_path = sys.argv[2] if len(sys.argv) > 2 else "/tmp/rs_sb3/Project/project.json"
py_data = load_project(py_path)
rs_data = load_project(rs_path)
py_procs = extract_procedures(py_data.get("targets", []))
rs_procs = extract_procedures(rs_data.get("targets", []))
all_procs = sorted(set(list(py_procs.keys()) + list(rs_procs.keys())))
header = "{:<55} {:>8} {:>8} {:>8}".format("Procedure", "Python", "Rust", "Diff")
print(header)
print("-" * len(header))
total_diff = 0
for proc in all_procs:
py_count = py_procs.get(proc, -1)
rs_count = rs_procs.get(proc, -1)
diff = rs_count - py_count if py_count >= 0 and rs_count >= 0 else 0
total_diff += diff
diff_str = "{:+d}".format(diff) if diff != 0 else "+0"
marker = " <<<" if diff != 0 else " OK"
print("{:<55} {:>8} {:>8} {:>8}{}".format(proc, py_count, rs_count, diff_str, marker))
print("\nTotal diff: {:+d}".format(total_diff))