From 4242e6915d96df7c645502540f06ad1920fd55ec Mon Sep 17 00:00:00 2001 From: sourcehold Date: Sat, 3 Jan 2026 10:44:40 +0100 Subject: [PATCH 01/14] [IDE] use cpp.hint files to help IDEs --- src/precomp/cpp.hint | 1 + 1 file changed, 1 insertion(+) create mode 100644 src/precomp/cpp.hint diff --git a/src/precomp/cpp.hint b/src/precomp/cpp.hint new file mode 100644 index 0000000..502ca8e --- /dev/null +++ b/src/precomp/cpp.hint @@ -0,0 +1 @@ +#define MACRO_STRUCT_RESOLVER \ No newline at end of file From 99072619c2e93e13dd1ad38b94e3b0b6fcc2ae28 Mon Sep 17 00:00:00 2001 From: sourcehold Date: Mon, 12 Jan 2026 09:54:36 +0100 Subject: [PATCH 02/14] [TOOLS] reccmp add gitignore file --- reccmp/.gitignore | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 reccmp/.gitignore diff --git a/reccmp/.gitignore b/reccmp/.gitignore new file mode 100644 index 0000000..53005d2 --- /dev/null +++ b/reccmp/.gitignore @@ -0,0 +1,4 @@ +reccmp-build.yml + +*.txt +*.json From 27f44a3b782e36a69a43a50f3e9638f9749faead Mon Sep 17 00:00:00 2001 From: sourcehold Date: Mon, 12 Jan 2026 10:08:35 +0100 Subject: [PATCH 03/14] [PROJECT] ignore python files and binary files --- .gitignore | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.gitignore b/.gitignore index c2b00cf..87d3d05 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,10 @@ # reccmp-user.yml # reccmp-build.yml +*.7z +*.sarif +*.bin +__pycache__ # OpenSHC project specific: build-*/ From 0f369ed2897bd3604f21bb56c2205c5ff0501d84 Mon Sep 17 00:00:00 2001 From: sourcehold Date: Mon, 12 Jan 2026 10:10:40 +0100 Subject: [PATCH 04/14] [SOURCE] include precomp assertion and addresses enum include --- src/precomp/.gitignore | 1 + src/precomp/assertion.h | 7 +++++++ src/precomp/pch.h | 2 ++ 3 files changed, 10 insertions(+) create mode 100644 src/precomp/.gitignore create mode 100644 src/precomp/assertion.h diff --git a/src/precomp/.gitignore b/src/precomp/.gitignore new file mode 100644 index 0000000..b4bdc95 --- /dev/null +++ b/src/precomp/.gitignore @@ -0,0 +1 @@ +addresses-SHC-3BB0A8C1.hpp \ No newline at end of file diff --git a/src/precomp/assertion.h b/src/precomp/assertion.h new file mode 100644 index 0000000..e225c55 --- /dev/null +++ b/src/precomp/assertion.h @@ -0,0 +1,7 @@ +/** + AUTO_GENERATED: DO NOT TOUCH THIS FILE + path: 'util/assertion.h' +*/ + +#define static_assert_cpp98(condition) typedef int _static_assert_cpp98_obj[(condition) ? 1 : -1]; +#define static_assert_cpp98_obj(condition, obj) typedef int _static_assert_cpp98 ## _ ## obj[(condition) ? 1 : -1]; \ No newline at end of file diff --git a/src/precomp/pch.h b/src/precomp/pch.h index 39742ad..3b7e0a2 100644 --- a/src/precomp/pch.h +++ b/src/precomp/pch.h @@ -3,6 +3,8 @@ #pragma once +#include "addresses-SHC-3BB0A8C1.hpp" +#include "assertion.h" #include "CompileMacros.h" #include "FunctionResolver.h" #include "StructResolver.h" From b19ccf88b01c6bfa860c49d032afe42246437ae8 Mon Sep 17 00:00:00 2001 From: sourcehold Date: Mon, 12 Jan 2026 10:23:22 +0100 Subject: [PATCH 05/14] [PROJECT] add tmp folder to gitignore --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index 87d3d05..c3dd856 100644 --- a/.gitignore +++ b/.gitignore @@ -3,6 +3,7 @@ *.7z *.sarif *.bin +/tmp __pycache__ From 99ae8f7f56f340044ee378757c550d9449c19430 Mon Sep 17 00:00:00 2001 From: sourcehold Date: Mon, 12 Jan 2026 10:26:34 +0100 Subject: [PATCH 06/14] [PROJECT] add convert3 python file --- convert3.py | 106 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 106 insertions(+) create mode 100644 convert3.py diff --git a/convert3.py b/convert3.py new file mode 100644 index 0000000..edc7904 --- /dev/null +++ b/convert3.py @@ -0,0 +1,106 @@ +from typing import List +from skink.architecture.enums import Enum, EnumResult +from skink.export.project.project import Project +from skink.export.project.collection import ExportedContentCollection, ExportContents +from skink.architecture.structs.struct import Struct +from skink.architecture.unions.union import Union +from skink.architecture.functionsignatures import FunctionSignature +from skink.architecture.typedefs import Typedef +from skink.sarif.datatypes.DataTypeResult import DataTypeResult +from skink.sarif.datatypes.FunctionSignatureResult import FunctionSignatureResult +from skink.sarif.datatypes.UnionResult import UnionResult +from skink.sarif.BasicResult import BasicResult +from skink.sarif.datatypes.TypedefResult import TypedefResult +import logging +logging.getLogger().setLevel(logging.DEBUG) +from skink.export.classes.collect import collect_classes, collect_namespaced_functions +import pathlib +from skink.export.styles.style3.exporter import Exporter, BinaryContext, TransformationRules, FileRules + +project = Project("Stronghold Crusader.exe.all.sarif", cache_objects=True, cache_symbols_to_path=".cached-symbols.bin") + +# TODO: permit_overwrite = False +logging.log(logging.INFO, "processing all symbol results") +project.process_all_symbol_results(log_progress=1000, store_symbol_result=True, permit_overwrite=True) +logging.log(logging.INFO, "processing all symbol results: finished") + +# objs_i = 0 +# for _ in project.yield_raw_objects(): +# objs_i += 1 +# print(objs_i) +import pickle +if pathlib.Path(".cached-objs.bin").exists() == False: + logging.log(logging.INFO, "finding all by location") + objs: List[BasicResult] = [] + objs_i = 0 + for obj in project.find_all_by_location(location="/_HoldStrong", recursive=True, lookup_lsymbols=True): + objs_i += 1 + print(f"{objs_i}\t\t{obj.ruleId}") + objs.append(obj) + logging.log(logging.INFO, "finding all by location: finished") + with open(".cached-objs.bin", 'wb') as f: + pickle.dump(file=f, obj=objs) +else: + with open(".cached-objs.bin", 'rb') as f: + objs = pickle.load(file=f) + +logging.log(logging.INFO, "collecting classes") +clsses = list(collect_classes(objs)) +logging.log(logging.INFO, "collecting classes: finished") + +logging.log(logging.INFO, "collecting namespaced functions") +namespaced_functions = list(collect_namespaced_functions(objs)) +logging.log(logging.INFO, "collecting namespaced functions: finished") + +bc = BinaryContext(hash="3BB0A8C1", abbreviation="SHC", reccmp_binary="STRONGHOLDCRUSADER") +exporter = Exporter(binary_context=bc, transformation_rules=TransformationRules(use_regex = True, regex={"_HoldStrong": "OpenSHC"}), expose_original_methods=True, + file_rules = FileRules(one_file_per_function=True, one_file_per_method=True)) + +collection = ExportedContentCollection(ignore_duplicates=True) + +collection.add(*exporter.export_helpers()) + +for cls in clsses: + collection.add(*exporter.export_class(cls)) + +for ns in namespaced_functions: + collection.add(*exporter.export_namespace(ns)) + +collection.add(exporter.export_addresses(project.yield_objects())) + +from skink.export.context import DEFAULT, Context +ctx: Context = DEFAULT.copy() # type: ignore +ctx.class_rules.suffix = "" +ctx.struct_rules.suffix = "" +ctx.include.file_extension = "" + +class_paths = set(cls.location(ctx) for cls in clsses) + +for obj in objs: + if isinstance(obj, DataTypeResult): + if obj.message.text == "DT.Struct": + global S + s = Struct(obj) + if s.name == "GameSynchronyState": + S = s + if s.path(ctx) not in class_paths: + collection.add(exporter.export_struct(s)) + elif isinstance(obj, EnumResult): + e = Enum(obj) + if e.er.properties.additionalProperties.size == 4: + collection.add(exporter.export_enum(e)) + else: + collection.add(*exporter.export_sized_enum(e)) + elif isinstance(obj, UnionResult): + e = Union(obj) + collection.add(exporter.export_union(e)) + elif isinstance(obj, FunctionSignatureResult): + fsr = FunctionSignature(obj) + collection.add(exporter.export_function_signature(fsr)) + elif isinstance(obj, TypedefResult): + td = Typedef(obj) + if "*" in td.name: + continue + collection.add(exporter.export_typedef(td)) + +collection.write_to_disk(pathlib.Path("src/"), overwrite_all=True) From 4b9956ec81a6bfcc289f172d1cf5b437a09fbbf7 Mon Sep 17 00:00:00 2001 From: Gynt Date: Mon, 12 Jan 2026 10:03:23 +0100 Subject: [PATCH 07/14] [BUILD] Update CMakeLists.txt to make src/ a valid header folder --- CMakeLists.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index bf476b3..893829e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -97,7 +97,10 @@ link_libraries( set(PCH_FILE ${CMAKE_SOURCE_DIR}/src/precomp/pch.h) file_dependent_read_list("${CMAKE_SOURCE_DIR}/cmake/core-sources.txt" CORE_SOURCES) - +# Make src/ a valid include directory +include_directories( + ${CMAKE_SOURCE_DIR}/src +) # Add source to this project's executable. add_executable(OpenSHC.exe WIN32 ${CORE_SOURCES}) From 381ecebcdedaf6be2658d8a6a2766da93c25f72e Mon Sep 17 00:00:00 2001 From: sourcehold Date: Tue, 13 Jan 2026 10:25:58 +0100 Subject: [PATCH 08/14] [CONVERSION] add arguments to convert3.py to clear conversion cache --- convert3.py | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/convert3.py b/convert3.py index edc7904..f5cf42e 100644 --- a/convert3.py +++ b/convert3.py @@ -17,7 +17,17 @@ import pathlib from skink.export.styles.style3.exporter import Exporter, BinaryContext, TransformationRules, FileRules -project = Project("Stronghold Crusader.exe.all.sarif", cache_objects=True, cache_symbols_to_path=".cached-symbols.bin") +import argparse +parser = argparse.ArgumentParser() +parser.add_argument("--sarif", required=False, default="Stronghold Crusader.exe.all.sarif") +parser.add_argument("--clear-cache", required=False, action='store_true', default=False) +args = parser.parse_args() + +if args.clear_cache: + pathlib.Path(".cached-symbols.bin").unlink() + pathlib.Path(".cached-objs.bin").unlink() + +project = Project(args.sarif, cache_objects=True, cache_symbols_to_path=".cached-symbols.bin") # TODO: permit_overwrite = False logging.log(logging.INFO, "processing all symbol results") From 59d29aa0a1266e8241a006af6f7c17cceb9dfd35 Mon Sep 17 00:00:00 2001 From: TheRedDaemon <66257843+TheRedDaemon@users.noreply.github.com> Date: Sun, 4 Jan 2026 15:13:51 +0100 Subject: [PATCH 09/14] [CMAKE] add build presets --- CMakeLists.txt | 2 +- CMakePresets.json | 36 ++++++++++++++++++++++++++++++++---- create-include-lists.cmake | 2 +- 3 files changed, 34 insertions(+), 6 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 893829e..efd7790 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,6 +1,6 @@ # CMakeList.txt : CMake project for OpenSHC -cmake_minimum_required (VERSION 3.20) +cmake_minimum_required (VERSION 3.21) # NOTE: POST_BUILD does not run if the target is unchanged, so a config switch will not trigger them again, so clean + build if issues happen function(target_file_copy_if_different TARGET FILE DEST) diff --git a/CMakePresets.json b/CMakePresets.json index 22cd0ed..0052602 100644 --- a/CMakePresets.json +++ b/CMakePresets.json @@ -2,12 +2,12 @@ "version": 3, "cmakeMinimumRequired": { "major": 3, - "minor": 19, + "minor": 21, "patch": 0 }, "configurePresets": [ { - "name": "nmake-base", + "name": "configure-base", "hidden": true, "generator": "NMake Makefiles", "binaryDir": "${sourceDir}/build-${presetName}", @@ -41,7 +41,7 @@ }, { "name": "Debug", - "inherits": "nmake-base", + "inherits": "configure-base", "description": "VS2005 NMake (Debug) x86", "cacheVariables": { "CMAKE_BUILD_TYPE": "${presetName}" @@ -49,11 +49,39 @@ }, { "name": "RelWithDebInfo", - "inherits": "nmake-base", + "inherits": "configure-base", "description": "VS2005 NMake (RelWithDebInfo) x86", "cacheVariables": { "CMAKE_BUILD_TYPE": "${presetName}" } } + ], + "buildPresets": [ + { + "name": "build-base", + "hidden": true, + "environment": { + "VSINSTALLDIR": "${sourceDir}/MSVC1400", + "VCINSTALLDIR": "${sourceDir}/MSVC1400/VC", + "FrameworkDir": "C:/WINDOWS/Microsoft.NET/Framework", + "FrameworkVersion": "v2.0.50727", + "FrameworkSDKDir": "${sourceDir}/MSVC1400/SDK/v2.0", + "DevEnvDir": "${sourceDir}/MSVC1400/Common7/IDE", + "PATH": "${sourceDir}/MSVC1400/Common7/IDE;${sourceDir}/MSVC1400/VC/bin;${sourceDir}/MSVC1400/Common7/Tools;${sourceDir}/MSVC1400/Common7/Tools/Bin;${sourceDir}/MSVC1400/VC/PlatformSDK/Bin;C:/WINDOWS/Microsoft.NET/Framework/v2.0.50727", + "INCLUDE": "${sourceDir}/MSVC1400/VC/include;${sourceDir}/MSVC1400/VC/PlatformSDK/Include", + "LIB": "${sourceDir}/MSVC1400/VC/lib;${sourceDir}/MSVC1400/VC/PlatformSDK/Lib", + "LIBPATH": "C:/WINDOWS/Microsoft.NET/Framework/v2.0.50727" + } + }, + { + "name": "Debug", + "inherits": "build-base", + "configurePreset": "Debug" + }, + { + "name": "RelWithDebInfo", + "inherits": "build-base", + "configurePreset": "RelWithDebInfo" + } ] } diff --git a/create-include-lists.cmake b/create-include-lists.cmake index 38c96eb..8d5792d 100644 --- a/create-include-lists.cmake +++ b/create-include-lists.cmake @@ -5,7 +5,7 @@ # Usage: cmake -P generate_file_list.cmake # ====================================================================== -cmake_minimum_required(VERSION 3.20) +cmake_minimum_required(VERSION 3.21) function(generate_file_list SOURCE_ROOT PATTERNS_LIST OUTPUT_FILE) set(ALL_ENTRIES "") From 5f088dd1db8275f202a0a773911fed1d6808761a Mon Sep 17 00:00:00 2001 From: TheRedDaemon <66257843+TheRedDaemon@users.noreply.github.com> Date: Sun, 4 Jan 2026 16:28:29 +0100 Subject: [PATCH 10/14] [BUILD] rework build script and update docs --- README.md | 5 +-- build.bat | 121 ++++++++++++++---------------------------------------- 2 files changed, 33 insertions(+), 93 deletions(-) diff --git a/README.md b/README.md index 123e8d4..5f874b8 100644 --- a/README.md +++ b/README.md @@ -59,12 +59,11 @@ Additionally, it configures format-on-save and a debug target for the UCP3. If the scripts are preferred, the following triggers a build using the scripts: 1. Open a terminal. If the Visual Studio CMake version is used, it needs to be the CMD developer command prompt. 2. Navigate to this project folder -3. Invoke vsvars32-portable.bat from the MSVC1400 in the developer command prompt session. Check with `where cl.exe` to see if it was successful: cl.exe and link.exe are supposed to be executed from your MSVC1400 folder. `where cmake` should point to your CMake installation. -4. Execute build.bat: +3. Execute build.bat: ```sh build.bat RelWithDebInfo ``` -5. Compare a function byte by byte to check compilation: +4. Compare a function byte by byte to check compilation: ```sh reccmp/run reccmp-reccmp --target STRONGHOLDCRUSADER --verbose 0x401000 ``` diff --git a/build.bat b/build.bat index 2311a6c..ec7c650 100644 --- a/build.bat +++ b/build.bat @@ -1,70 +1,17 @@ @echo off setlocal EnableDelayedExpansion -:: --- Validate task parameter (clean, build, rebuild) --- +:: --- Validate preset parameter (required) --- if "%~1"=="" ( - echo [ERROR] Task not specified. - echo Usage: %~nx0 [clean^|build^|rebuild] [BuildType] + echo [ERROR] Preset not specified. + echo Usage: %~nx0 ^ [Target] + echo ^ : Required. The CMake configure/build preset to use. + echo [Target] : Optional. The specific target to build. If omitted, the default target will be built. exit /b 1 ) -set "TASK=%~1" - -if /I not "%TASK%"=="clean" if /I not "%TASK%"=="build" if /I not "%TASK%"=="rebuild" ( - echo [ERROR] Invalid task: "%TASK%" - echo Valid tasks are: clean, build, rebuild - exit /b 1 -) - -:: --- Validate build type parameter (must be only letters) --- -if "%~2"=="" ( - echo [ERROR] Build type not specified. - echo Usage: %~nx0 [clean^|build^|rebuild] [BuildType] - exit /b 1 -) - -:: --- Validate that is is at least all letters, also need to use "." hack due to piping issue with *$ in findstr (. consumes \r) --- -echo %~2 | findstr /R "^[a-zA-Z][a-zA-Z]*.$" >nul -if errorlevel 1 ( - echo [ERROR] Invalid build type: "%~2" - echo It must only contain letters ^(e.g., Debug, Release^). - exit /b 1 -) - -:: --- Set build directory --- -set "BUILD_DIR=build-%~2" - -:: --- Clean build directory if task is clean or rebuild --- -if /I not "%TASK%"=="build" ( - if exist "%BUILD_DIR%" ( - echo Cleaning build directory "%BUILD_DIR%"... - rmdir /S /Q "%BUILD_DIR%" - if errorlevel 1 ( - echo [ERROR] Failed to clean build directory "%BUILD_DIR%". - exit /b 1 - ) - echo Clean completed successfully. - ) else ( - echo Build directory "%BUILD_DIR%" does not exist. Nothing to clean. - ) -) - -:: --- If task is clean only, exit after cleaning --- -if /I "%TASK%"=="clean" ( - exit /b 0 -) - -:: --- Check and load old environment into context --- -set "VSVARS=MSVC1400\vsvars32-portable.bat" -if not exist "%VSVARS%" ( - echo [ERROR] Could not find environment setup script: %VSVARS% - exit /b 1 -) -call "%VSVARS%" -if errorlevel 1 ( - echo [ERROR] Failed to execute: %VSVARS% - exit /b 2 -) +set "PRESET=%~1" +set "TARGET=%~2" :: --- Check for cmake --- where cmake >nul 2>nul @@ -74,7 +21,9 @@ if errorlevel 1 ( echo [ERROR] 'vswhere' not found, cannot locate 'cmake'. exit /b 1 ) - FOR /F "tokens=* USEBACKQ" %%g IN (`"C:\Program Files (x86)\Microsoft Visual Studio\Installer\vswhere.exe" -latest -property installationPath -requires Microsoft.VisualStudio.Component.VC.CMake.Project`) do (SET "CMAKE=%%g\Common7\IDE\CommonExtensions\Microsoft\CMake\CMake\bin") + FOR /F "tokens=* USEBACKQ" %%g IN (`"C:\Program Files (x86)\Microsoft Visual Studio\Installer\vswhere.exe" -latest -property installationPath -requires Microsoft.VisualStudio.Component.VC.CMake.Project`) do ( + SET "CMAKE=%%g\Common7\IDE\CommonExtensions\Microsoft\CMake\CMake\bin" + ) echo [INFO] Detected: "!CMAKE!" if not exist "!CMAKE!" ( echo [ERROR] 'cmake' is not found in PATH and not found using vswhere. @@ -83,13 +32,6 @@ if errorlevel 1 ( set "PATH=!CMAKE!;%PATH%" ) -:: --- Check for nmake --- -where nmake >nul 2>nul -if errorlevel 1 ( - echo [ERROR] 'nmake' is not found in PATH. - exit /b 1 -) - :: --- Kill mspdbsrv.exe if it's running --- tasklist | find /I "mspdbsrv.exe" >nul if not errorlevel 1 ( @@ -97,33 +39,32 @@ if not errorlevel 1 ( taskkill /f /t /im mspdbsrv.exe >nul if errorlevel 1 ( echo [WARNING] Failed to stop mspdbsrv.exe, continuing... - ) -) - -:: --- Create build directory --- -if not exist "%BUILD_DIR%" ( - mkdir "%BUILD_DIR%" >nul 2>&1 - if errorlevel 1 ( - echo [ERROR] Failed to create build directory "%BUILD_DIR%". - exit /b 1 ) ) -:: --- Run cmake and nmake --- -pushd "%BUILD_DIR%" -cmake .. -G "NMake Makefiles" -DCMAKE_BUILD_TYPE=%~2 +:: --- Run cmake configure using preset --- +echo [INFO] Configuring with preset "%PRESET%"... +cmake --preset "%PRESET%" if errorlevel 1 ( - echo [ERROR] cmake failed. - popd + echo [ERROR] CMake configure failed for preset "%PRESET%". exit /b 1 ) -nmake -if errorlevel 1 ( - echo [ERROR] nmake build failed. - popd - exit /b 1 +:: --- Run cmake build using preset --- +if "%TARGET%"=="" ( + echo [INFO] Building preset "%PRESET%" with default target... + cmake --build --preset "%PRESET%" + if errorlevel 1 ( + echo [ERROR] CMake build failed for preset "%PRESET%". + exit /b 1 + ) + echo Build completed successfully for preset "%PRESET%". +) else ( + echo [INFO] Building preset "%PRESET%" with target "%TARGET%"... + cmake --build --preset "%PRESET%" --target "%TARGET%" + if errorlevel 1 ( + echo [ERROR] CMake build failed for preset "%PRESET%" target "%TARGET%". + exit /b 1 + ) + echo Build completed successfully for preset "%PRESET%" target "%TARGET%". ) - -popd -echo Build completed successfully for "%~2" configuration. From fd9c32647322dbc19e4ad38c63731bc26c564da4 Mon Sep 17 00:00:00 2001 From: sourcehold Date: Fri, 9 Jan 2026 20:44:39 +0100 Subject: [PATCH 11/14] [BUILD] add support for finding cmake in Microsoft.VisualStudio.Product.BuildTools environments --- build.bat | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/build.bat b/build.bat index ec7c650..00aa1d9 100644 --- a/build.bat +++ b/build.bat @@ -24,11 +24,16 @@ if errorlevel 1 ( FOR /F "tokens=* USEBACKQ" %%g IN (`"C:\Program Files (x86)\Microsoft Visual Studio\Installer\vswhere.exe" -latest -property installationPath -requires Microsoft.VisualStudio.Component.VC.CMake.Project`) do ( SET "CMAKE=%%g\Common7\IDE\CommonExtensions\Microsoft\CMake\CMake\bin" ) - echo [INFO] Detected: "!CMAKE!" + if not exist "!CMAKE!" ( + FOR /F "tokens=* USEBACKQ" %%g IN (`"C:\Program Files (x86)\Microsoft Visual Studio\Installer\vswhere.exe" -latest -property installationPath -requires Microsoft.VisualStudio.Component.VC.CMake.Project -products Microsoft.VisualStudio.Product.BuildTools` ) do ( + SET "CMAKE=%%g\Common7\IDE\CommonExtensions\Microsoft\CMake\CMake\bin" + ) + ) if not exist "!CMAKE!" ( echo [ERROR] 'cmake' is not found in PATH and not found using vswhere. exit /b 1 ) + echo [INFO] Detected: "!CMAKE!" set "PATH=!CMAKE!;%PATH%" ) From 6a54dd074dc70b361ebfe720c7c71ebdf4c894f1 Mon Sep 17 00:00:00 2001 From: sourcehold Date: Thu, 15 Jan 2026 23:30:26 +0100 Subject: [PATCH 12/14] [PROJECT] add polyfill directory for C++03 polyfills --- src/precomp/{common.h => common.hpp} | 14 ++++++++------ src/precomp/pch.h | 4 ++-- src/precomp/{ => polyfills}/assertion.h | 0 3 files changed, 10 insertions(+), 8 deletions(-) rename src/precomp/{common.h => common.hpp} (80%) rename src/precomp/{ => polyfills}/assertion.h (100%) diff --git a/src/precomp/common.h b/src/precomp/common.hpp similarity index 80% rename from src/precomp/common.h rename to src/precomp/common.hpp index 8f5a1cf..801fb06 100644 --- a/src/precomp/common.h +++ b/src/precomp/common.hpp @@ -1,7 +1,9 @@ -#pragma once +/** + AUTO_GENERATED: DO NOT TOUCH THIS FILE + path: 'precomp/common.hpp' +*/ -#define MAP_XY_LIMIT 400 -#define MAP_XY_LIMIT_INCLUSIVE 399 +#pragma once namespace Ghidra { typedef void* pointer; @@ -11,7 +13,7 @@ typedef unsigned char undefined; // typedef unsigned char bool; typedef unsigned char byte; typedef unsigned int dword; -// typedef unsigned long long GUID; // different then the Windows one? +// typedef unsigned long long GUID; typedef pointer32 ImageBaseOffset32; typedef long long longlong; @@ -23,13 +25,13 @@ typedef unsigned long ulong; typedef unsigned long long ulonglong; typedef unsigned char undefined1; typedef unsigned short undefined2; -typedef unsigned int undefined3; +typedef unsigned char undefined3[3]; typedef unsigned int undefined4; typedef unsigned long long undefined6; typedef unsigned long long undefined8; typedef unsigned short ushort; // typedef short wchar_t; typedef unsigned short word; -} // namespace Ghidra +} using namespace Ghidra; diff --git a/src/precomp/pch.h b/src/precomp/pch.h index 3b7e0a2..f08522a 100644 --- a/src/precomp/pch.h +++ b/src/precomp/pch.h @@ -4,10 +4,10 @@ #pragma once #include "addresses-SHC-3BB0A8C1.hpp" -#include "assertion.h" +#include "polyfills/assertion.h" #include "CompileMacros.h" #include "FunctionResolver.h" #include "StructResolver.h" #include "TypeUtility.h" -#include "common.h" +#include "common.hpp" #include "framework.h" diff --git a/src/precomp/assertion.h b/src/precomp/polyfills/assertion.h similarity index 100% rename from src/precomp/assertion.h rename to src/precomp/polyfills/assertion.h From 402f895f60c95a7cc82c764076945ef4a0f9ca74 Mon Sep 17 00:00:00 2001 From: sourcehold Date: Thu, 15 Jan 2026 23:56:00 +0100 Subject: [PATCH 13/14] [CONVERSION] add source folder argument to python script --- convert3.py | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/convert3.py b/convert3.py index f5cf42e..0f99bb7 100644 --- a/convert3.py +++ b/convert3.py @@ -12,7 +12,7 @@ from skink.sarif.BasicResult import BasicResult from skink.sarif.datatypes.TypedefResult import TypedefResult import logging -logging.getLogger().setLevel(logging.DEBUG) + from skink.export.classes.collect import collect_classes, collect_namespaced_functions import pathlib from skink.export.styles.style3.exporter import Exporter, BinaryContext, TransformationRules, FileRules @@ -21,11 +21,18 @@ parser = argparse.ArgumentParser() parser.add_argument("--sarif", required=False, default="Stronghold Crusader.exe.all.sarif") parser.add_argument("--clear-cache", required=False, action='store_true', default=False) +parser.add_argument("--output-dir", required=False, default='src') +parser.add_argument("--verbose", default=False, action='store_true') args = parser.parse_args() +if args.verbose: + logging.getLogger().setLevel(logging.DEBUG) + if args.clear_cache: - pathlib.Path(".cached-symbols.bin").unlink() - pathlib.Path(".cached-objs.bin").unlink() + if pathlib.Path(".cached-symbols.bin").exists(): + pathlib.Path(".cached-symbols.bin").unlink() + if pathlib.Path(".cached-objs.bin").exists(): + pathlib.Path(".cached-objs.bin").unlink() project = Project(args.sarif, cache_objects=True, cache_symbols_to_path=".cached-symbols.bin") @@ -113,4 +120,4 @@ continue collection.add(exporter.export_typedef(td)) -collection.write_to_disk(pathlib.Path("src/"), overwrite_all=True) +collection.write_to_disk(pathlib.Path(args.output_dir), overwrite_all=True) From 3a812b681fac9a55c918414633cb503543a58a25 Mon Sep 17 00:00:00 2001 From: Gynt Date: Sun, 18 Jan 2026 15:52:33 +0100 Subject: [PATCH 14/14] cleanup convert3.py --- convert3.py | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/convert3.py b/convert3.py index 0f99bb7..99cb920 100644 --- a/convert3.py +++ b/convert3.py @@ -17,6 +17,13 @@ import pathlib from skink.export.styles.style3.exporter import Exporter, BinaryContext, TransformationRules, FileRules +from skink.export.context import DEFAULT, Context +ctx: Context = DEFAULT.copy() # type: ignore +ctx.class_rules.suffix = "" +ctx.struct_rules.suffix = "" +ctx.include.file_extension = "" + + import argparse parser = argparse.ArgumentParser() parser.add_argument("--sarif", required=False, default="Stronghold Crusader.exe.all.sarif") @@ -85,12 +92,6 @@ collection.add(exporter.export_addresses(project.yield_objects())) -from skink.export.context import DEFAULT, Context -ctx: Context = DEFAULT.copy() # type: ignore -ctx.class_rules.suffix = "" -ctx.struct_rules.suffix = "" -ctx.include.file_extension = "" - class_paths = set(cls.location(ctx) for cls in clsses) for obj in objs: