|
11 | 11 | ### |
12 | 12 |
|
13 | 13 | import argparse |
| 14 | +import fnmatch |
14 | 15 | import os |
15 | 16 | import re |
16 | 17 | from typing import List |
|
19 | 20 | root_dir = os.path.abspath(os.path.join(script_dir, "..")) |
20 | 21 | src_dir = os.path.join(root_dir, "src") |
21 | 22 | include_dirs: List[str] = [] # Set with -I flag |
| 23 | +exclude_globs: List[str] = [] # Set with -x flag |
22 | 24 |
|
23 | 25 | include_pattern = re.compile(r'^#\s*include\s*[<"](.+?)[>"]') |
24 | 26 | guard_pattern = re.compile(r"^#\s*ifndef\s+(.*)$") |
|
28 | 30 | deps = [] |
29 | 31 |
|
30 | 32 |
|
| 33 | +def generate_prelude(defines) -> str: |
| 34 | + if len(defines) == 0: |
| 35 | + return "" |
| 36 | + |
| 37 | + out_text = "/* decompctx prelude */\n" |
| 38 | + for define in defines: |
| 39 | + parts = define.split("=", 1) |
| 40 | + if len(parts) == 2: |
| 41 | + macro_name, macro_val = parts |
| 42 | + out_text += f"#define {macro_name} {macro_val}\n" |
| 43 | + else: |
| 44 | + out_text += f"#define {parts[0]}\n" |
| 45 | + out_text += "/* end decompctx prelude */\n\n" |
| 46 | + |
| 47 | + return out_text |
| 48 | + |
| 49 | + |
31 | 50 | def import_h_file(in_file: str, r_path: str) -> str: |
32 | 51 | rel_path = os.path.join(root_dir, r_path, in_file) |
33 | 52 | if os.path.exists(rel_path): |
@@ -73,8 +92,17 @@ def process_file(in_file: str, lines: List[str]) -> str: |
73 | 92 | print("Processing file", in_file) |
74 | 93 | include_match = include_pattern.match(line.strip()) |
75 | 94 | if include_match and not include_match[1].endswith(".s"): |
| 95 | + excluded = False |
| 96 | + for glob in exclude_globs: |
| 97 | + if fnmatch.fnmatch(include_match[1], glob): |
| 98 | + excluded = True |
| 99 | + break |
| 100 | + |
76 | 101 | out_text += f'/* "{in_file}" line {idx} "{include_match[1]}" */\n' |
77 | | - out_text += import_h_file(include_match[1], os.path.dirname(in_file)) |
| 102 | + if excluded: |
| 103 | + out_text += "/* Skipped excluded file */\n" |
| 104 | + else: |
| 105 | + out_text += import_h_file(include_match[1], os.path.dirname(in_file)) |
78 | 106 | out_text += f'/* end "{include_match[1]}" */\n' |
79 | 107 | else: |
80 | 108 | out_text += line |
@@ -111,13 +139,29 @@ def main(): |
111 | 139 | help="""Include directory""", |
112 | 140 | action="append", |
113 | 141 | ) |
| 142 | + parser.add_argument( |
| 143 | + "-x", |
| 144 | + "--exclude", |
| 145 | + help="""Excluded file name glob""", |
| 146 | + action="append", |
| 147 | + ) |
| 148 | + parser.add_argument( |
| 149 | + "-D", |
| 150 | + "--define", |
| 151 | + help="""Macro definition""", |
| 152 | + action="append", |
| 153 | + ) |
114 | 154 | args = parser.parse_args() |
115 | 155 |
|
116 | 156 | if args.include is None: |
117 | 157 | exit("No include directories specified") |
118 | 158 | global include_dirs |
119 | 159 | include_dirs = args.include |
120 | | - output = import_c_file(args.c_file) |
| 160 | + global exclude_globs |
| 161 | + exclude_globs = args.exclude or [] |
| 162 | + prelude_defines = args.define or [] |
| 163 | + output = generate_prelude(prelude_defines) |
| 164 | + output += import_c_file(args.c_file) |
121 | 165 |
|
122 | 166 | with open(os.path.join(root_dir, args.output), "w", encoding="utf-8") as f: |
123 | 167 | f.write(output) |
|
0 commit comments