Skip to content

Releases: gigaHours/Gibbed.MadMax

Gibbed.MadMax-1.6.0

Choose a tag to compare

@gigaHours gigaHours released this 12 Mar 17:27

Highlights

This release migrates the entire solution to .NET 8.0, adds ADF serialization (import) support, and introduces two new command-line tools for modding workflows.

What's New

.NET 8.0 Migration

  • All projects now target net8.0, replacing the legacy .NET Framework 4.8 / multi-target builds.
  • Removed legacy AssemblyInfo.cs files and app.config files in favor of SDK-style project conventions.
  • Added Directory.Build.props for unified output path configuration.
  • Solution file cleaned up and modernized.

ADF Serializer (Import Support)

  • AdfFile.Serialize() is now fully implemented — ADF files can be written back to binary, enabling round-trip editing workflows.
  • ConvertAdf import mode is no longer a stub — XML-to-ADF conversion is fully functional.
  • Type definitions are now exported to and imported from XML (<typedefs> section).
  • Instance metadata (nameHash, typeHash) is preserved in XML output for lossless round-trips.
  • RuntimeTypeLibrary gained GetTypeDefinitionByName() for type lookups during import.

New Tool: Gibbed.MadMax.BinarySearch

  • Search for byte patterns across game archive files with support for little-endian, big-endian, or both.
  • Multi-threaded search with configurable patterns.

New Tool: Gibbed.MadMax.ResolveHashes

  • Resolve hash values in XML files using project hash lists.
  • Supports in-place replacement with optional comment annotations showing original hashes.

Bug Fixes

  • BytesVariant.Parse(): Fixed off-by-one iteration bug (i += 2i++) that skipped every other byte when parsing comma-separated byte values.
  • BytesVariant.Parse(): Added null/empty string handling to avoid crashes on empty byte arrays.
  • SmallUnpack: Replaced deprecated Assembly.CodeBase with Assembly.Location for .NET 8.0 compatibility.
  • ProjectData: Added PlatformNotSupportedException handling for cross-platform compatibility.
  • ConvertAdf export: Output path now appends .xml instead of replacing the extension, preserving original filenames like file.adf.xml.

Gibbed.MadMax-1.5.6

Choose a tag to compare

@gigaHours gigaHours released this 25 Feb 19:17

Here's a release note:


ConvertProperty: Fix crash on empty vec_byte values

Fixed a FormatException crash when converting RTPC properties containing empty vec_byte fields (e.g. _decoration_info in CRoadObject).

Also fixed a pre-existing bug where BytesVariant.Parse only read every other byte (i += 2 instead of i++), silently corrupting multi-byte values during round-trip.

Gibbed.MadMax-1.5.5

Choose a tag to compare

@gigaHours gigaHours released this 19 Feb 19:42

Bug Fixes

Fix: Library modules broken after decompile/recompile

Library modules (lib_*.xvmc) use flags: 0x1 to register their functions as globals so other scripts can call them. This flag was silently dropped during decompilation, causing recompiled library modules to stop working — any script depending on them would fail at runtime.

29 out of 842 game scripts are affected (all lib_*.xvmc files).

The decompiler now emits #! flags: 0x1 automatically, and the compiler preserves it through to the output .xvmc.

Fix: Missing trailing ret 0 sentinel

The compiler omitted the trailing ret 0 when a function's last statement was already a return. This caused the decompiler's CFG builder to lose if blocks whose jump targets pointed past the last instruction.

Fix: break statement and structural analysis

  • Added break statement support inside while loops
  • Fixed while-loop exit block causing post-loop code to be absorbed into the loop body
  • Fixed elif chains breaking when the merge point coincided with an outer loop exit

Fix: stitem stack order

The decompiler and compiler had the wrong pop/push order for index store operations (obj[idx] = val), producing invalid code for scripts using indexed assignment.

New Directive: #! flags:

The #! flags: directive is emitted automatically by the decompiler for library modules. It is not gated by --hashes because it affects runtime behavior.

Value Meaning Files in game
0x0 Standard script 813
0x1 Library module 29

Known Differences (non-functional)

Round-tripped files may differ from originals in constant ordering, StringBuffer layout, max_stack values (precise vs over-estimated), and omission of dead-code jmp instructions after ret. All differences are functionally equivalent.

Gibbed.MadMax-1.5.4

Choose a tag to compare

@gigaHours gigaHours released this 19 Feb 17:47

Fix: Compiler missing trailing ret 0 sentinel

Bug: The compiler omitted the implicit ret 0 at the end of functions when the last statement was already a return. This caused jz/jmp labels targeting the end of the function to point past the last instruction (out-of-bounds). On subsequent decompilation, the CFG builder couldn't create a block for the invalid target, reducing a 2-successor jz block to 1 successor — which made the decompiler silently drop if guards.

Impact: Any function ending with if ...: return ... (no else) would lose the if condition on round-trip, turning conditional returns into unconditional ones.

Examples from enemy_boarding_gameplay.xvmc:

  • GetPositionSB — third if 1.0 == GetStateBit(char, 22.0): return 22.0 became unconditional return 22.0 (function now returns 22.0 even when no state bit is set, instead of none)
  • CheckAttackLockif local2 and local3: guard was dropped, causing GetBlackboardValueFromObject to be called with a potentially null vehicle reference

Fix: Always emit ret 0 at the end of every function, matching the Avalanche compiler behavior. One line changed in CodeGenerator.cs.

Gibbed.MadMax-1.5.3

Choose a tag to compare

@gigaHours gigaHours released this 19 Feb 17:13

Release 1.5.3

break statement support + decompiler bug fixes

New feature: break keyword

  • The break statement is now fully supported in the decompiler, compiler, and round-trip pipeline
  • Exits the enclosing while loop, matching Python semantics

Decompiler fixes (StructuralAnalysis):

  • Fixed break inside while loops — previously emitted as pass, causing all post-loop code to be absorbed into the loop body. Scripts like lib_vehicleupgrades.xvmc (RecomputeGearbox) produced functionally broken output when recompiled.
  • Fixed elif body absorbing subsequent statementsFindLinearEnd could advance past the stop block, causing code after an if/elif chain to be pulled inside the last branch (e.g. MassCompensateSuspensionLength).
  • Fixed elif chains collapsing into nested ifs — merge point detection failed when the merge coincided with the outer exit block, breaking flat elif chains into deeply nested if blocks with misplaced return statements (e.g. DiminishingReturnsProgression).

StoreItem bug fix:

  • Fixed stitem stack order in both the decompiler (ExpressionRecovery) and compiler (CodeGenerator). The XVM convention is push value, push obj, push indexstitem pops index, obj, val.

Batch directory mode:

  • Decompiler and compiler now accept a directory as input, recursively processing all .xvmc / .xvm files. Supports drag-and-drop of folders onto the .exe.

Affected files:

  • StructuralAnalysis.cs — region-based control flow recovery with break support
  • Ast.cs / AstPrinter.csBreakStmt AST node
  • Token.cs / Lexer.cs / Parser.cs / CodeGenerator.csbreak compilation
  • ExpressionRecovery.cs / CodeGenerator.csstitem stack order fix
  • XvmDecompile/Program.cs / XvmCompile/Program.cs — batch directory mode

Gibbed.MadMax-1.5.2

Choose a tag to compare

@gigaHours gigaHours released this 18 Feb 18:30

What's New

Bug Fixes

  • Fixed stitem (StoreItem) stack order in both decompiler and compiler — the XVM stack convention for indexed assignment (obj[index] = value) was incorrectly handled, causing decompilation of scripts with array/list indexing operations (e.g. lib_vehicleupgrades.xvmc) to produce invalid code that could not be recompiled

New Features

  • Batch directory mode for XvmDecompile and XvmCompile — drag a folder onto the .exe or pass a directory path to recursively process all .xvmc / .xvm files. Reports success/failure counts on completion

Documentation

  • Fixed stitem stack order documentation across all XVM reference docs and assembly guides
  • Added batch mode usage instructions
  • Updated tool descriptions in README (EN/RU) and project documentation

Full Changelog: updated-1.5.1...1.5.2

Gibbed.MadMax-1.5.1

Choose a tag to compare

@gigaHours gigaHours released this 08 Feb 14:28

What's New

🔄 Decompiler & Compiler

  • XvmDecompile — decompile .xvmc bytecode to high-level Python-like .xvm source
  • XvmCompile — compile .xvm source back to .xvmc bytecode
  • Full round-trip: decompile → edit → compile → drop into game

✨ Compiler Features

  • Auto-computed function name hashes (Jenkins lookup3)
  • Auto-computed source_hash, max_stack, and locals
  • Debug info generation (line:column per instruction)
  • Constant folding for negative float literals
  • #! hash: / #! source_hash: directives for exact binary reproduction

🐛 Bug Fixes

  • Fixed Jenkins hash for strings with length divisible by 12 (e.g. DisableBoost)
  • Fixed importHashes not being assigned during XvmModule.Deserialize()

📖 Documentation

  • Complete XVM language reference (English | Russian)
  • Full engine API reference in xvm_globals.txt — 49 modules, 900+ methods with type signatures
  • Updated README with high-level and low-level workflow examples

Workflow

Decompile
Gibbed.MadMax.XvmDecompile.exe script.xvmc script.xvm

Edit the .xvm file...
Compile
Gibbed.MadMax.XvmCompile.exe script.xvm script.xvmc

Drop into game
copy script.xvmc /dropzone/scripts/...

Gibbed.MadMax-1.5

Choose a tag to compare

@gigaHours gigaHours released this 07 Feb 19:05
image

Changes

  • XvmAssemble — assembles .dis files back into .xvmc bytecode with full ADF packaging
  • debug_info round-trip — disassembler emits @line:col annotations, assembler rebuilds the debug_info ADF instance (type 0xDCB06466). The game requires debug_info for proper script execution
  • debug_strings round-trip — attribute/global names preserved through disassembly and reassembly
  • Bug fixImportHashes were silently dropped during XvmModule.Deserialize() (read to local variable but never assigned to the module)

Known Differences vs Original Binaries

Reassembled .xvmc files are functionally identical to originals. Minor binary-level differences (constant ordering, StringBuffer layout, StringHashes count) do not affect script execution.

Documentation

Please refer to the project documentation before use:

Gibbed.MadMax-1.3

Choose a tag to compare

@gigaHours gigaHours released this 15 Oct 19:14

Снимок экрана 2024-10-15 220024

  • Update Serialize/Deserialize vec_events type (ConvertProperty.exe)
    • Deserializing with hash lookups
    • Serializing from string to hash
      • if a string starts with 0x or 0X, then this is considered as a direct serialization from the hexadecimal representation
  • Fixed a bug with reading .bin files (Raw Property)
    • fixed reading a matrix from 3x4 to 4x4

if you edited a file opened by a previous version, it must be reopened!

Gibbed-Updated-1.2

Choose a tag to compare

@gigaHours gigaHours released this 18 Aug 22:36

Fixed ConvertProperty (.blo -> .xml -> .blo)

  • Fix invalid matrix type (4x3 -> 4x4)
  • Fix Alignment PropertyFormats
    If you converted to xml on the old version, you need to convert the original file again!