Winelib SAPI4 host: MSTTS (Sam/Mary/Mike) + AT&T Flextalk (Keith Bell/Kerry Watson)
This commit is contained in:
Executable
+112
@@ -0,0 +1,112 @@
|
||||
#!/usr/bin/env python3
|
||||
"""Convert INF AddReg sections into a Windows/Wine .reg file.
|
||||
|
||||
Example:
|
||||
inf2reg.py --section APIReg --define 49000='C:\\windows\\speech' \
|
||||
spchapi/SPCHAPI.INF > spchapi.reg
|
||||
"""
|
||||
import argparse
|
||||
import re
|
||||
import sys
|
||||
|
||||
ROOTS = {
|
||||
"HKCR": "HKEY_CLASSES_ROOT",
|
||||
"HKLM": "HKEY_LOCAL_MACHINE",
|
||||
"HKCU": "HKEY_CURRENT_USER",
|
||||
"HKU": "HKEY_USERS",
|
||||
}
|
||||
|
||||
|
||||
def expand(text, defines):
|
||||
def repl(m):
|
||||
key = m.group(1)
|
||||
if key == "25":
|
||||
return defines.get("WINDOWS", r"C:\windows")
|
||||
return defines.get(key, m.group(0))
|
||||
|
||||
return re.sub(r"%(\w+)%", repl, text)
|
||||
|
||||
|
||||
def reg_type(flags, data):
|
||||
if not flags:
|
||||
return "REG_SZ"
|
||||
try:
|
||||
f = int(flags, 16) if flags.lower().startswith("0x") else int(flags)
|
||||
except ValueError:
|
||||
return "REG_SZ"
|
||||
if f & 0x00020000:
|
||||
return "REG_EXPAND_SZ"
|
||||
if f & 0x00010000:
|
||||
return "REG_MULTI_SZ"
|
||||
if f & 0x00000001:
|
||||
return "REG_BINARY"
|
||||
return "REG_SZ"
|
||||
|
||||
|
||||
def reg_escape(value):
|
||||
return value.replace("\\", "\\\\").replace('"', '\\"')
|
||||
|
||||
|
||||
def unquote(token):
|
||||
token = token.strip()
|
||||
if len(token) >= 2 and token[0] == '"' and token[-1] == '"':
|
||||
return token[1:-1]
|
||||
return token
|
||||
|
||||
|
||||
def main():
|
||||
ap = argparse.ArgumentParser()
|
||||
ap.add_argument("inf")
|
||||
ap.add_argument("--section", action="append", required=True,
|
||||
help="AddReg section name (repeatable)")
|
||||
ap.add_argument("--define", action="append", default=[],
|
||||
help="ID=value, e.g. 49000=C:\\windows\\speech")
|
||||
args = ap.parse_args()
|
||||
|
||||
defines = {"WINDOWS": r"C:\windows"}
|
||||
for item in args.define:
|
||||
k, v = item.split("=", 1)
|
||||
defines[k] = v
|
||||
|
||||
wanted = set(args.section)
|
||||
section = None
|
||||
out = ["REGEDIT4", ""]
|
||||
|
||||
with open(args.inf, "r", encoding="latin-1") as fh:
|
||||
for raw in fh:
|
||||
line = raw.strip()
|
||||
if not line or line.startswith(";"):
|
||||
continue
|
||||
m = re.match(r"^\[([^\]]+)\]$", line)
|
||||
if m:
|
||||
section = m.group(1)
|
||||
continue
|
||||
if section not in wanted:
|
||||
continue
|
||||
parts = [p.strip() for p in line.split(",")]
|
||||
if len(parts) < 4:
|
||||
continue
|
||||
root, key, name, flags = parts[0], parts[1], parts[2], parts[3]
|
||||
data = ",".join(parts[4:]) if len(parts) > 4 else ""
|
||||
if root.upper() not in ROOTS:
|
||||
continue
|
||||
data = expand(unquote(data), defines)
|
||||
name = expand(unquote(name), defines)
|
||||
if "%InstallPrompt%" in name:
|
||||
continue
|
||||
if not data:
|
||||
continue
|
||||
rtype = reg_type(flags.strip(), data)
|
||||
keypath = "\\".join(
|
||||
p for p in (ROOTS[root.upper()], expand(key, defines)) if p
|
||||
)
|
||||
value = data if rtype == "REG_BINARY" else '"%s"' % reg_escape(data)
|
||||
out.append("[%s]" % keypath)
|
||||
out.append("%s=%s" % ('@' if not name else '"%s"' % name, value))
|
||||
out.append("")
|
||||
|
||||
sys.stdout.write("\n".join(out) + "\n")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
Reference in New Issue
Block a user