Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .agents/skills/AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,4 @@
- State each skill's platform scope explicitly; keep Android and iOS procedures separate.
- Describe reusable workflows in terms of the target extension. Named extensions may be optional examples, never mandatory dependencies for unrelated ports.
- Obtain build commands, versions, artifact names, and paths from the target extension's current scripts and configuration. Do not treat one extension's settings as repository-wide defaults.
- Every extension/platform skill must preserve the standing repository-layout rule in fusion-extension-porting/SKILL.md: adapt existing libraries in place with narrow macros or in the corresponding platform component directory. Apply this to future ports automatically; do not invent mobile subtrees in Windows plugin/library projects.
17 changes: 16 additions & 1 deletion .agents/skills/fusion-android-porting/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ description: Port Clickteam Fusion C++ extensions to Android, or diagnose Androi
## Scope

Apply the [common porting rules](../fusion-extension-porting/SKILL.md), including
Git checkout normalization and artifact hash verification, before this workflow.
Git checkout normalization and artifact verification, before this workflow.

Use this skill only for Fusion Android/JNI implementation, builds, publishing, or troubleshooting.
For a multi-platform task, apply it to the Android portion; still assess shared C++ changes for their
Expand All @@ -19,8 +19,23 @@ Keep algorithms in shared C++; use Java for Fusion Runtime integration and JNI m
Compile native libraries during extension development/publishing, then let Fusion use its own
default build templates when exporting an APK.

If encryption or encrypted assets are involved, also read and follow
[`fusion-shared-encryption`](../fusion-shared-encryption/SKILL.md). Reusing its source
is not sufficient: mobile plugins must consume one shared encryption runtime.

## Establish the target

Apply the common skill's standing repository-layout requirement to every plugin
and dependency adaptation without asking the author to restate it.

Keep Android implementation and development assets under
`Extensions/Android_Gradle`, following its existing Java/JNI, `cmake/<Plugin>`
and `tests/<plugin>` layout. `Extensions/<Plugin>` is the Windows VS project;
do not add an Android or Mobile subtree there or in Windows library directories.
Adapt an existing library in its original files with narrow macros, or put its
Android-specific code under the corresponding app/src/main component directory.
Preserve existing `ToInstall` distribution paths.

1. Identify the extension, its Windows ACE definitions, existing mobile code, and the installed
Fusion Runtime and development SDK versions.
2. Inspect repository instructions, branch state, and local changes. Preserve unrelated work.
Expand Down
34 changes: 34 additions & 0 deletions .agents/skills/fusion-extension-porting/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,40 @@ or [iOS porting](../fusion-ios-porting/SKILL.md) for the relevant target.
Derive paths and commands from the target project; do not require another plugin.
Write skills and repository documentation in English.

## Repository layout

This is a standing author requirement for every plugin and library port, not a
Fini-specific convention. Apply it automatically at the start of future work;
do not wait for the author to repeat it or ask them to choose the layout again.

The original `Extensions` tree contains Windows Visual Studio projects and their
libraries. Android_Gradle and iOS are independent platform project roots, even
though their current repository paths are nested below Extensions. Do not treat
that historical nesting as a reason to put mobile adaptations into Windows
library directories.

`Extensions/<Plugin>` is the Windows Visual Studio project directory. Keep iOS
projects, adapters, build scripts, tests and native handoff inputs under
`Extensions/iOS/<Plugin>`. Keep Android adapters, JNI sources, CMake/toolchain
configuration, tests and documentation under `Extensions/Android_Gradle`, using
its existing source/cmake/test directories. Do not nest `iOS`, `Android` or
`Mobile` development trees inside a Windows plugin or library directory. For
library adaptations, either extend the original source with narrow platform or
feature macros, or put platform-specific code under the corresponding platform
project's component/source directory (Android uses app/src/main). Reuse the
original implementation; do not create a second cipher or algorithm copy.
Existing `ToInstall` release layouts and VS publishing hooks remain
the distribution entry points, not platform development roots.

Before creating or moving files, determine whether each file extends an existing
shared implementation or belongs to a platform project. Use the original file
with a narrow macro for the former, and the corresponding platform component
directory for the latter. A shared runtime does not justify putting Android/iOS
build, packaging or handoff trees in a Windows library directory. Follow existing
platform paths; their historical nesting does not authorize relocating the whole
platform project. After a move, update includes, build/project references,
publishers, manifests and documentation, and verify the resulting source inventory.

Use the current Windows C++ implementation as the behavioral reference for
portable features. Reuse shared algorithms; adapt platform-specific object,
resource and Runtime access through the actual target SDK. Keep shared C++
Expand Down
36 changes: 27 additions & 9 deletions .agents/skills/fusion-ios-porting/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,15 +17,25 @@ for other plugins. Write this skill, references and operational docs in English.
Preserve shared C++ interfaces; submit shared behavioral changes for author review.
Keep private SDK/exporter material outside the public repository.

Apply the common skill's standing repository-layout requirement to every plugin
and dependency adaptation without asking the author to restate it. Adapt existing
libraries in their original files with narrow macros, or put iOS-specific
integration under the iOS project's corresponding component directory. Keep
Apple build, packaging and handoff inputs there, outside Windows library trees.

If encryption is involved, also apply
[shared encryption](../fusion-shared-encryption/SKILL.md): that runtime is an
author-approved shared service, not a rule to dynamically split every helper.

## Workflow

1. Inspect current Windows ACE definitions, mobile adapters, the installed exporter
and a real exported project. Inventory IDs, property layout, parameter decoding,
events, selection, creation and unsupported operations before implementation.
2. Treat the Windows C++ implementation as the behavioral oracle for portable
features. Add direct comparisons against its actual classes for paths, flags,
units/ZOC, area layers, line ranges, AOE and caching; do not use Android output
as the specification. Adapt only platform-specific I/O/object mechanics using
features. Add direct comparisons against its actual classes for the target
plugin's data, flags, numeric/string semantics and caching; do not use Android
output as the specification. Adapt only platform-specific I/O/object mechanics using
the actual iOS SDK. Reuse computational algorithms in shared C++. Keep Runtime objects, selection,
creation and event dispatch in an owned adapter. Compare helpers with current
Windows and Android versions; preserve each Runtime's actual representations.
Expand All @@ -39,12 +49,16 @@ Keep private SDK/exporter material outside the public repository.
fixed-width values, explicit buffer/string lengths and exception translation.
Avoid STL and C++ layout exposure. Retain owners across callback reentrancy;
snapshot iteration results and define destruction/replacement behavior.
4. Keep each plugin's build project under Extensions/iOS/<Plugin>. Use CMake and
4. Keep the plugin's iOS project, Runtime adapter, build scripts, tests and native
handoff inputs under Extensions/iOS/<Plugin>. Extensions/<Plugin> is its VS
project; do not put iOS or Mobile development trees there. Use CMake and
Ninja/Make for scripted compilation; use Apple CLI tools for SDK selection and
XCFramework creation. Full Xcode supplies iOS SDKs; standalone Command Line
Tools are insufficient. Do not require opening Xcode GUI to build the core.
5. Build separate iOS device and simulator platform slices. The current task
supports arm64 only; do not add Intel/Rosetta/32-bit targets. Use a static
5. Build separate iOS device and simulator platform slices. Derive architectures
from the target project and author requirements. The FTW reference uses arm64
only; do not make that a universal rule or add Intel/Rosetta/32-bit slices
without a target requirement. Use a static
XCFramework when it matches the exported project's linking model. Prebuilding
isolates language settings, not the deployment availability of libc++ APIs.
6. Stage binaries with source/configuration and per-file hashes, normalize Git
Expand All @@ -56,7 +70,9 @@ Keep private SDK/exporter material outside the public repository.
7. Publish the extension as .ext, including required native and adapter material.
Native-only manifests are valid inputs to a Windows packager: verify compiled
dependencies, then package the current Runtime adapter there. Do not force a
Mac rebuild merely because the thin source adapter changed.
Mac rebuild for adapter sources shipped separately from the compiled core.
If an adapter is compiled into the transferred library, its changes do require
a rebuild; record that boundary instead of applying a blanket exemption.
Validate its actual encoding and export round trip; do not rename an arbitrary
ZIP to .ext. Fusion may export files without adding their Xcode references.
Verify library/source references, include paths, system dependencies and final
Expand Down Expand Up @@ -95,8 +111,10 @@ Keep private SDK/exporter material outside the public repository.

## Reusable Runtime helpers and exported-project patches

Use `Helpers/ObjectBase.h`, `ObjectSelection.h` and `ObjectCreation.h` as separate
generic classes, with common OI access in ObjectBase. Compare the current Windows
When lookup/selection/creation infrastructure is needed, use the maintained
`Helpers/ObjectBase.h`, `ObjectSelection.h` and `ObjectCreation.h` as separate
generic classes, with common OI access in ObjectBase. Do not add a plugin core
dependency merely to obtain these helpers or import unused plugin semantics. Compare the current Windows
`Extensions/_3rdLib/Object*.h` and Android `_3rdLib` counterparts, including APIs
not yet used by the consuming extension. Do not rename them for that extension.

Expand Down
71 changes: 71 additions & 0 deletions .agents/skills/fusion-shared-encryption/SKILL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
---
name: fusion-shared-encryption
description: Reuse and publish the common encryption runtime when porting or updating Fusion plugins. Prevent private per-plugin crypto implementations and preserve the Mac build/push to Windows pull/VS packaging workflow. Covers shared contracts; platform procedures are separate references.
---

# Shared encryption for Fusion plugins

## Scope

Use when a plugin consumes encryption, key derivation or encrypted assets, or when
changing the shared mobile encryption library/build/distribution. This is a shared
runtime contract, not permission to alter unrelated plugins or merge a PR.
Apply [common porting rules](../fusion-extension-porting/SKILL.md), including
compiled-component assessment and text/binary digest policy. Read the relevant
[Android](../fusion-android-porting/SKILL.md) or
[iOS](../fusion-ios-porting/SKILL.md) workflow before platform changes.

The shared encryption runtime is an explicit author requirement for this project.
It does not imply that every utility header, template or plugin algorithm should
be moved into a DLL. Keep small/stateless helpers modular; assess actual emitted
code, state ownership and exporter deployment before introducing another boundary.

## Required architecture

- Reuse `Extensions/_DeLib/Encryption`; preserve existing cipher, key derivation,
Unicode and asset formats. Do not write a Java, Objective-C or plugin-local cipher.
- **Shared means shared by plugins at runtime**, not merely common source copied
or statically linked into every plugin. Clients include `Encryption/CAPI.h`
and call the stable `Encryption_*` C ABI. Keep algorithms, KeyGen and OpenSSL
inside the single common runtime. Its implementation stays in the original
`Encryption` sources; Android build integration lives under
`Android_Gradle/app/src/main/cpp/Encryption` and iOS build integration under
`iOS/Encryption`. Do not add a Mobile subtree to the Windows library.
- Do not put libcrypto, a private encryption implementation, or a renamed copy of
the common library in each plugin package. Interface headers are permitted.
Publish/build/cache the common runtime independently and declare client dependencies.
- Keep OpenSSL/C++ implementation symbols private; export only the supported C ABI.
Validate ABI/version, target architectures, library identity and compatible STL.
Never silently overwrite a conflicting common runtime already installed by another plugin.
- Inspect current shared modules and the target plugin's real publisher/VS hooks
before adding another tool path. Reference existing publishing scripts (such as
FTW) for discovery, incremental builds, errors, copy/install and archive behavior;
do not invent a second manual delivery path or treat FTW-specific constants as universal.

## Cross-machine handoff

When Apple compilation belongs to the author, generate the real Xcode project,
shared schemes and commands even if the agent has no Xcode. The Mac build stages
owned plugin and common-library artifacts separately with SHA256/source manifests.
The author compiles and pushes those files; Windows git pull receives them, and
VS RunOnly invokes the publisher to validate, generate and update distribution
packages. Windows must not require Xcode or rebuild Apple code. Do not push
unbuilt placeholders or claim Apple/device validation from project-generation tests.

Preserve signing, runtime loader and exporter constraints. A generated ZIP is not proof of exporter integration. For the supported legacy
format, reuse the independent `.ext` codec and validate the decoded payload and
six project-insertion blocks. Distinguish a verified package from a successful
export, final link or device test.
Do not redistribute licensed exporter headers, Runtime sources or test projects.

## Validation and review

Check the client binary's actual dynamic references and absence of defined crypto
symbols, shared runtime exports, all supported slices, separate package ownership,
hashes/stale-source rejection and one-time dependency installation. Include failure
checks for missing, corrupt or conflicting artifacts. Run the actual publishing
entry point. Distinguish host fixtures, target builds, APK/exporter builds and devices.
Keep shared source changes reviewable and open/update the requested PR; do not merge.

- Android procedure: [references/android.md](references/android.md)
- iOS/Mac-to-Windows procedure: [references/ios.md](references/ios.md)
26 changes: 26 additions & 0 deletions .agents/skills/fusion-shared-encryption/references/android.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# Android shared encryption

Use alongside fusion-android-porting and android-runtime-parity. Keep Fusion object
access/events in Java and algorithms in C++; use JNI to call the plugin native core.
The plugin library imports libofe_encryption.so through the C ABI. Only that common
library links libcrypto. Reuse
`Android_Gradle/app/src/main/cpp/Encryption/CMakeLists.txt` and
`Android_Gradle/cmake/Encryption/android_runtime.py`; both consume the original
Encryption sources. Keep Android adaptations in its platform project.

Use one common build/cache/output across plugins. Emit a separate OFEEncryption.zip
with matching libc++_shared.so, licenses, ABI/version and hashes. Client ZIPs own only
their JNI library/Java/resources and an explicit dependency; no common implementation
or duplicate crypto binaries. Do not replace application Gradle/ProGuard/Runtime files.
Stage the common dependency once in the final exported app, with conflict/hash checks.
Do not assume Fusion includes an arbitrary common ZIP just because it is installed.

Follow the target publisher's SDK/NDK/CMake/Ninja discovery and sdkmanager preparation
flow; search installed SDK/VS/PATH tools first. Keep work/cache/logs outside commits.
Check actual readiness after installation. Preserve proxy and certificate settings.

Inspect DT_NEEDED/SONAME and dynamic symbols: the client imports Encryption_* from
the common library and defines no encryption/EVP implementation. The shared library
exports its C ABI and hides EVP symbols. Inspect each ABI's final package and APK,
including one compatible STL. Apply 16 KiB checks to supported 64-bit Android targets;
do not misreport the NDK's 32-bit 4 KiB STL as a broken 64-bit build.
34 changes: 34 additions & 0 deletions .agents/skills/fusion-shared-encryption/references/ios.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# iOS shared encryption and Mac-to-Windows delivery

Use Objective-C++ to call the existing C++ plugin core and Encryption C ABI; JNI is
Android-only. Fini's standalone project is an example, not a dependency for other ports.
Build a client archive/XCFramework without libcrypto. Build one dynamic
OFEEncryption.framework/XCFramework through `iOS/Encryption/build.py` for all plugins, with a
stable install name and C export list. Embed/sign the common framework once in the app.
Keep its native handoff inputs in `iOS/Encryption/Prebuilt` and build tooling in
the iOS platform project; compile the original Encryption sources directly.

Generate an actual .xcodeproj and shared schemes on the agent host. Configure local
licensed Runtime header paths through an ignored local xcconfig. Keep public SDK
locations portable and supply device/simulator build targets. A missing Xcode prevents
Apple compilation, not generation of the requested project and delivery scripts.

Honor this repository's author handoff: Mac builds -> separately stages owned client
and shared artifacts with manifests -> author commits/pushes -> Windows git pull ->
VS RunOnly's existing publisher validates/stages those artifacts and creates/updates
release packages. Preserve the single publishing entry point and propagate errors.
Do not ask the author to manually reconstruct packages after every Mac build.

Do not run git push from the Mac build script, commit machine-local configs or include
licensed SDK source. The author controls publishing compiled Apple files. Windows can
skip Apple packaging while no Mac build is available, but must reject incomplete,
corrupt or source-stale committed artifacts without replacing a known-good package.

Preserve the verified PR #100 .ext flow: Windows consumes native artifacts and
packages the current loader/adapter using the independent shared format codec.
Verify decoded payload/CRC and PBX insertion blocks. A native XCFramework ZIP
alone is not an installable .ext, and a valid .ext is not proof of final linkage.
Use an idempotent target-aware configurator for missing exported project references;
preserve device signing, unrelated extensions/flags and a higher deployment floor.
Validate generated project syntax/references and the Mac/Windows manifest handoff
without calling those checks an Apple build. The author supplies Apple/device results.
4 changes: 4 additions & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
# Native handoff archives stay byte-exact across Mac and Windows checkouts.
*.xcframework.zip binary
*.a binary
*.ext binary
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -25,3 +25,6 @@ __pycache__/
# Generated OpenSSL SDK, vcpkg checkout and dependency caches
/Extensions/_3rdLib/Encrypt-sdk/
/Extensions/_3rdLib/Encrypt-build/out/

# Local builds, toolchains, downloads and verification logs
/work/
Loading
Loading