diff --git a/cve_bin_tool/checkers/python.py b/cve_bin_tool/checkers/python.py index f7ae562b79..0e8e841481 100644 --- a/cve_bin_tool/checkers/python.py +++ b/cve_bin_tool/checkers/python.py @@ -25,5 +25,6 @@ class PythonChecker(Checker): r"([23]+\.[0-9]+\.[0-9]+)\r?\nPython %s", r"([23]+\.[0-9]+\.[0-9]+)\r?\n%\.80s \(%\.80s\) %\.80s", r"tags/v([23]+\.[0-9]+\.[0-9]+)\r?\n", + r"Python\n([23]+\.[0-9]+\.[0-9]+)\nPython Software Foundation", ] VENDOR_PRODUCT = [("python_software_foundation", "python"), ("python", "python")] diff --git a/cve_bin_tool/version_scanner.py b/cve_bin_tool/version_scanner.py index 7940e51f96..b061546bee 100644 --- a/cve_bin_tool/version_scanner.py +++ b/cve_bin_tool/version_scanner.py @@ -231,6 +231,34 @@ def is_linux_kernel(self, filename: str) -> tuple[bool, str | None]: return False, output + # used to get product name, version, vendor info PE metadata + def extract_version_from_pe(self, filename: str) -> str: + info = "" + try: + import pefile + + with pefile.PE(filename) as pe: + # pe = pefile.PE(filename) + for fileinfo in pe.FileInfo: + for entry in fileinfo: + if entry.Key == b"StringFileInfo": + for st in entry.StringTable: + entries = st.entries + product_name = entries.get(b"ProductName", b"").decode( + errors="ignore" + ) + product_version = entries.get( + b"ProductVersion", b"" + ).decode(errors="ignore") + company_name = entries.get(b"CompanyName", b"").decode( + errors="ignore" + ) + info = f"{product_name}\n{product_version}\n{company_name}\n" + self.logger.debug(f"peFile.PE Metadata:{info}") + except Exception as e: + LOGGER.debug(f"[PE Metadata] Failed to parse PE file {filename}: {e}") + return info + def scan_file(self, filename: str) -> Iterator[ScanInfo]: """Scans a file to see if it contains any of the target libraries, and whether any of those contain CVEs""" @@ -261,6 +289,9 @@ def scan_file(self, filename: str) -> Iterator[ScanInfo]: # parse binary file's strings lines = parse_strings(filename) + # lines += self.extract_version_from_pe(filename) + ver_info = self.extract_version_from_pe(filename) + lines += ver_info if self.no_scan: yield from self.run_checkers(filename, lines)