From 781edc1b203a5cd7fe8978408407a655ea3b280a Mon Sep 17 00:00:00 2001 From: bhavyabhardwaj001 <161822108+bhavyabhardwaj001@users.noreply.github.com> Date: Mon, 8 Jun 2026 15:34:35 +0530 Subject: [PATCH 1/4] fix(backend): correct GHDL version regex parsing --- src/toolManager/tool_manager_windows.py | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/toolManager/tool_manager_windows.py b/src/toolManager/tool_manager_windows.py index 5cd42e1ea..d19e5ba6b 100644 --- a/src/toolManager/tool_manager_windows.py +++ b/src/toolManager/tool_manager_windows.py @@ -294,7 +294,7 @@ def find_ghdl(version=None): try: result = run_cmd_safe([str(custom_exe), "--version"]) if result and result.returncode == 0: - match = re.search(r'GHDL\s+(\d+\.\d+\.\d+)', result.stdout) + match = re.search(r'GHDL\s+(\d+\.\d+(?:\.\d+)?)', result.stdout) if match: found_ver = match.group(1) if version is None or found_ver.startswith(str(version)): @@ -309,7 +309,7 @@ def find_ghdl(version=None): try: result = run_cmd_safe([str(msys2_ghdl), "--version"]) if result and result.returncode == 0: - match = re.search(r'GHDL\s+(\d+\.\d+\.\d+)', result.stdout) + match = re.search(r'GHDL\s+(\d+\.\d+(?:\.\d+)?)', result.stdout) if match: found_ver = match.group(1) if version is None or found_ver.startswith(str(version)): @@ -322,7 +322,7 @@ def find_ghdl(version=None): try: result = run_cmd_safe([ghdl_exe, "--version"]) if result and result.returncode == 0: - match = re.search(r'GHDL\s+(\d+\.\d+\.\d+)', result.stdout) + match = re.search(r'GHDL\s+(\d+\.\d+(?:\.\d+)?)', result.stdout) if match: found_ver = match.group(1) if version is None or found_ver.startswith(str(version)): @@ -945,8 +945,8 @@ def _ghdl_hook(n, bs, total): result = run_cmd_safe([str(dest_exe), "--version"]) if result and result.returncode == 0: - match = re.search(r'GHDL\s+(\d+\.\d+\.\d+)', result.stdout) - version = match.group(1) if match else v + match = re.search(r'GHDL\s+(\d+\.\d+(?:\.\d+)?)', result.stdout) + version = match.group(1) if match else "unknown" print(f"[OK] GHDL {version} ready to use") print_status("installed", version, v) else: From f4738296f1b7ec5f3b6400e3f495b0a8345402f6 Mon Sep 17 00:00:00 2001 From: bhavyabhardwaj001 <161822108+bhavyabhardwaj001@users.noreply.github.com> Date: Mon, 8 Jun 2026 15:51:16 +0530 Subject: [PATCH 2/4] fix(core): resolve subprocess PATH inheritance for MSYS2 DLLs --- src/toolManager/tool_manager_windows.py | 18 +++++++++++++++--- src/toolManager/utils.py | 10 ++++++---- 2 files changed, 21 insertions(+), 7 deletions(-) diff --git a/src/toolManager/tool_manager_windows.py b/src/toolManager/tool_manager_windows.py index d19e5ba6b..f8a165d12 100644 --- a/src/toolManager/tool_manager_windows.py +++ b/src/toolManager/tool_manager_windows.py @@ -287,6 +287,18 @@ def find_pyqt_fixed(version=None): pass return None, None +def get_msys2_env(): + env = os.environ.copy() + paths = [] + msys_bin = get_msys2_mingw_bin() + if msys_bin: paths.append(str(msys_bin)) + msys_root = get_msys2_mingw_root() + if msys_root: + usr_bin = msys_root.parent / "usr" / "bin" + if usr_bin.exists(): paths.append(str(usr_bin)) + if paths: + env["PATH"] = os.pathsep.join(paths) + os.pathsep + env.get("PATH", "") + return env def find_ghdl(version=None): custom_exe = BASE_DIR / "bin" / "ghdl.exe" @@ -307,7 +319,7 @@ def find_ghdl(version=None): msys2_ghdl = msys_bin / "ghdl.exe" if msys2_ghdl.exists(): try: - result = run_cmd_safe([str(msys2_ghdl), "--version"]) + result = run_cmd_safe([str(msys2_ghdl), "--version"], env=get_msys2_env()) if result and result.returncode == 0: match = re.search(r'GHDL\s+(\d+\.\d+(?:\.\d+)?)', result.stdout) if match: @@ -339,7 +351,7 @@ def find_verilator(version=None): msys2_exe = msys_bin / exe_name if msys2_exe.exists(): try: - result = run_cmd_safe([str(msys2_exe), "--version"], timeout=10) + result = run_cmd_safe([str(msys2_exe), "--version"], timeout=10, env=get_msys2_env()) if result and result.returncode == 0: for line in result.stdout.split('\n'): if "Verilator" in line: @@ -943,7 +955,7 @@ def _ghdl_hook(n, bs, total): shutil.copy2(ghdl_exe, dest_exe) print(f"[OK] Installed to: {dest_exe}") - result = run_cmd_safe([str(dest_exe), "--version"]) + result = run_cmd_safe([str(dest_exe), "--version"], env=get_msys2_env()) if result and result.returncode == 0: match = re.search(r'GHDL\s+(\d+\.\d+(?:\.\d+)?)', result.stdout) version = match.group(1) if match else "unknown" diff --git a/src/toolManager/utils.py b/src/toolManager/utils.py index 2481da5a6..093e5d094 100644 --- a/src/toolManager/utils.py +++ b/src/toolManager/utils.py @@ -56,7 +56,7 @@ # ==================== HELPERS ==================== -def run_cmd_safe(cmd, timeout=30, cwd=None): +def run_cmd_safe(cmd, timeout=30, cwd=None, env=None): """ Executes a command safely without showing a window on Windows. Returns the subprocess.CompletedProcess result or None if failed. @@ -81,14 +81,15 @@ def run_cmd_safe(cmd, timeout=30, cwd=None): creationflags=creationflags, encoding='utf-8', errors='ignore', - cwd=cwd + cwd=cwd, + env=env ) return result except Exception as e: print(f"Command failed: {e}") return None -def run_cmd_stream(cmd, timeout=900, cwd=None): +def run_cmd_stream(cmd, timeout=900, cwd=None, env=None): """ Executes a command and streams its output to stdout in real-time. Returns a tuple of (returncode, full_output_string). @@ -113,7 +114,8 @@ def run_cmd_stream(cmd, timeout=900, cwd=None): creationflags=cf, encoding='utf-8', errors='ignore', - cwd=cwd + cwd=cwd, + env=env ) output_lines = [] From 2b24bfc1c0d271cee1d7caa760146d7e52319291 Mon Sep 17 00:00:00 2001 From: bhavyabhardwaj001 <161822108+bhavyabhardwaj001@users.noreply.github.com> Date: Tue, 9 Jun 2026 11:15:39 +0530 Subject: [PATCH 3/4] fix(core): add finalization extraction status to prevent 99 percent stall confusion --- src/toolManager/tool_manager_windows.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/toolManager/tool_manager_windows.py b/src/toolManager/tool_manager_windows.py index f8a165d12..21c96985c 100644 --- a/src/toolManager/tool_manager_windows.py +++ b/src/toolManager/tool_manager_windows.py @@ -927,6 +927,7 @@ def _ghdl_hook(n, bs, total): with zipfile.ZipFile(zip_file, 'r') as zf: files = zf.namelist() print(f"Archive contains {len(files)} files") + print("[INFO] Extracting package... This may take several minutes.", flush=True) zf.extractall(install_dir) print("[OK] Extraction complete") except Exception as e: @@ -1023,7 +1024,7 @@ def _install_verilator_from_7z(archive_path, v): shutil.rmtree(extract_dir, ignore_errors=True) extract_dir.mkdir(parents=True, exist_ok=True) - print(f"[1/3] Extracting {archive_path.name}...") + print(f"[1/3] Extracting {archive_path.name}... This may take several minutes.", flush=True) try: with py7zr.SevenZipFile(archive_path, mode='r') as archive: archive.extractall(extract_dir) From fb38cbd08e61cb58a7b03dd25bcb5353320a818f Mon Sep 17 00:00:00 2001 From: bhavyabhardwaj001 <161822108+bhavyabhardwaj001@users.noreply.github.com> Date: Tue, 9 Jun 2026 11:26:31 +0530 Subject: [PATCH 4/4] fix: resolve status synchronization and eSim/Verilator detection logic --- src/toolManager/main.py | 2 ++ src/toolManager/tool_manager_windows.py | 4 +++- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/src/toolManager/main.py b/src/toolManager/main.py index a1c71f467..498b7adbd 100644 --- a/src/toolManager/main.py +++ b/src/toolManager/main.py @@ -112,6 +112,8 @@ def run(self): line = line.rstrip() if line: self.progress.emit(f" {line}") + if "[ERROR]" in line or "install_failed|" in line: + success = False proc.wait() if proc.returncode != 0: success = False diff --git a/src/toolManager/tool_manager_windows.py b/src/toolManager/tool_manager_windows.py index 21c96985c..de268df7a 100644 --- a/src/toolManager/tool_manager_windows.py +++ b/src/toolManager/tool_manager_windows.py @@ -1179,6 +1179,8 @@ def get_state_version(package_name): def check_esim(target_version): indicators = [ + BASE_DIR / "eSim.bat", + BASE_DIR / "src" / "frontEnd" / "Application.py", ESIM_DIR / "eSim.bat", ESIM_DIR / "uninst-eSim.exe", ESIM_DIR / "src" / "frontEnd" / "Application.py", @@ -1222,7 +1224,7 @@ def install_esim(target_version, upgrade=False): try: subprocess.run([str(installer), "/S"], timeout=1800) time.sleep(20) - for p in [ESIM_DIR / "eSim.bat", ESIM_DIR / "uninst-eSim.exe"]: + for p in [BASE_DIR / "eSim.bat", BASE_DIR / "src" / "frontEnd" / "Application.py", ESIM_DIR / "eSim.bat", ESIM_DIR / "uninst-eSim.exe"]: if p.exists(): update_state("esim", display_ver) print(f"[OK] eSim {display_ver} installed")