feat(amm): swap via d70225ced program_id_hex API; pin wallet-module core to sequencer rev 415964d7

This commit is contained in:
Andrea Franz 2026-07-17 16:13:29 +02:00 committed by r4bbit
parent 69cd58d377
commit 9b7a3dcaac
4 changed files with 81 additions and 63 deletions

47
Cargo.lock generated
View File

@ -83,7 +83,7 @@ dependencies = [
"amm_core", "amm_core",
"borsh", "borsh",
"cbindgen", "cbindgen",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0-rc6)", "lee_core",
"risc0-binfmt", "risc0-binfmt",
"risc0-zkvm", "risc0-zkvm",
"ruint", "ruint",
@ -96,7 +96,7 @@ version = "0.1.0"
dependencies = [ dependencies = [
"alloy-primitives", "alloy-primitives",
"borsh", "borsh",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"risc0-zkvm", "risc0-zkvm",
"ruint", "ruint",
"serde", "serde",
@ -110,7 +110,7 @@ version = "0.1.0"
dependencies = [ dependencies = [
"amm_core", "amm_core",
"clock_core", "clock_core",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"token_core", "token_core",
"twap_oracle_core", "twap_oracle_core",
] ]
@ -544,7 +544,7 @@ name = "ata_core"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"borsh", "borsh",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"risc0-zkvm", "risc0-zkvm",
"serde", "serde",
] ]
@ -554,7 +554,7 @@ name = "ata_program"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"ata_core", "ata_core",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"token_core", "token_core",
] ]
@ -974,7 +974,7 @@ version = "0.1.0"
source = "git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0#a58fbce2ff48c58b7bb5001b1a27e64b9596ee3a" source = "git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0#a58fbce2ff48c58b7bb5001b1a27e64b9596ee3a"
dependencies = [ dependencies = [
"borsh", "borsh",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
] ]
[[package]] [[package]]
@ -2175,7 +2175,7 @@ dependencies = [
"ata_core", "ata_core",
"clock_core", "clock_core",
"lee", "lee",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"stablecoin-methods", "stablecoin-methods",
"stablecoin_core", "stablecoin_core",
"token-methods", "token-methods",
@ -2351,7 +2351,7 @@ dependencies = [
"build_utils", "build_utils",
"hex", "hex",
"k256", "k256",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"log", "log",
"rand 0.8.6", "rand 0.8.6",
"risc0-binfmt", "risc0-binfmt",
@ -2379,23 +2379,6 @@ dependencies = [
"thiserror 2.0.18", "thiserror 2.0.18",
] ]
[[package]]
name = "lee_core"
version = "0.1.0"
source = "git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0-rc6#e37876a64028a335eb693198a1ed6a0e875ec5b4"
dependencies = [
"base58",
"borsh",
"bytemuck",
"bytesize",
"chacha20",
"ml-kem",
"risc0-zkvm",
"serde",
"serde_with",
"thiserror 2.0.18",
]
[[package]] [[package]]
name = "libc" name = "libc"
version = "0.2.186" version = "0.2.186"
@ -3847,7 +3830,7 @@ source = "git+https://github.com/logos-co/spel.git?tag=v0.6.0#0cb7e0980535af6194
dependencies = [ dependencies = [
"base58", "base58",
"borsh", "borsh",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"proc-macro2", "proc-macro2",
"serde", "serde",
"serde_json", "serde_json",
@ -3927,7 +3910,7 @@ version = "0.1.0"
dependencies = [ dependencies = [
"alloy-primitives", "alloy-primitives",
"borsh", "borsh",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"risc0-zkvm", "risc0-zkvm",
"ruint", "ruint",
"serde", "serde",
@ -3939,7 +3922,7 @@ dependencies = [
name = "stablecoin_program" name = "stablecoin_program"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"stablecoin_core", "stablecoin_core",
"token_core", "token_core",
] ]
@ -4153,7 +4136,7 @@ name = "token_core"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"borsh", "borsh",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"serde", "serde",
"spel-framework-macros", "spel-framework-macros",
] ]
@ -4162,7 +4145,7 @@ dependencies = [
name = "token_program" name = "token_program"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"token_core", "token_core",
] ]
@ -4382,7 +4365,7 @@ version = "0.1.0"
dependencies = [ dependencies = [
"alloy-primitives", "alloy-primitives",
"borsh", "borsh",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"risc0-zkvm", "risc0-zkvm",
"ruint", "ruint",
"serde", "serde",
@ -4395,7 +4378,7 @@ name = "twap_oracle_program"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"clock_core", "clock_core",
"lee_core 0.1.0 (git+https://github.com/logos-blockchain/logos-execution-zone.git?tag=v0.2.0)", "lee_core",
"twap_oracle_core", "twap_oracle_core",
] ]

View File

@ -32,13 +32,14 @@ extern "C" {
// arguments — including the account_id_to_base58 round-trips used to render // arguments — including the account_id_to_base58 round-trips used to render
// accounts — are NOT evaluated, so there's no per-call overhead. // accounts — are NOT evaluated, so there's no per-call overhead.
// //
// NOTE: `send_generic_public_transaction` takes `instruction` and // NOTE: `send_generic_public_transaction(account_ids, signing_requirements,
// `program_dependencies` as byte strings (`bstr`). Declaring them as Vec<u32> / // instruction, program_id_hex)`. `instruction` is a byte string (`bstr`):
// Vec<Vec<u8>> makes the module's Qt/QtRO glue downgrade them to an opaque `any` // declaring it as Vec<u32> makes the module's Qt/QtRO glue downgrade it to an
// the separate module process can't deserialize, silently dropping every // opaque `any` the separate module process can't deserialize, silently dropping
// argument. We therefore send `instruction` as the little-endian bytes of the // every argument. We send `instruction` as the little-endian bytes of the u32
// u32 words and `program_dependencies` empty. Requires the wallet module built // words, and the deployed program by its id hex (not the raw ELF). Requires the
// with byte-string params; see docs/amm-swap-qtro-serialization-bug.md. // wallet module built with the byte-string param; see
// docs/amm-swap-qtro-serialization-bug.md.
static bool ammDebugEnabled() static bool ammDebugEnabled()
{ {
static const bool on = qEnvironmentVariableIsSet("AMM_DEBUG"); static const bool on = qEnvironmentVariableIsSet("AMM_DEBUG");
@ -775,15 +776,38 @@ QString AmmUiBackend::swapExactInput(QString defAHex, QString defBHex, QString u
} }
// 6. Submit through the wallet module's generic public-transaction entry // 6. Submit through the wallet module's generic public-transaction entry
// point. `instruction` is sent as the little-endian bytes of the u32 words // point. The module API takes `instruction` (as bytes — see the note atop
// (see the note atop this file); program_dependencies is empty because the // this file) plus the program's id as hex, not the raw ELF: the program is
// sequencer resolves the AMM's chained token/twap calls on-chain for a // already deployed and referenced by id. There is no program_dependencies
// public tx. // arg — the sequencer resolves the AMM's chained token/twap calls on-chain.
const QByteArray instructionBytes(reinterpret_cast<const char*>(instruction.data()), const QByteArray instructionBytes(reinterpret_cast<const char*>(instruction.data()),
static_cast<int>(instruction.size() * sizeof(uint32_t))); static_cast<int>(instruction.size() * sizeof(uint32_t)));
// Derive the deployed AMM program id from the ELF and hex-encode it as the
// canonical 32-byte hex (little-endian per u32 word — matches `spel
// program-id` and the on-chain config's *_program_id fields).
ProgramId ammId;
if (!amm_client_program_id_from_elf(reinterpret_cast<const uint8_t*>(elf.constData()),
static_cast<uintptr_t>(elf.size()), &ammId)) {
qWarning() << "AmmUiBackend::swapExactInput: amm_client_program_id_from_elf failed";
return QString();
}
QByteArray programIdBytes;
programIdBytes.reserve(32);
for (int i = 0; i < 8; ++i) {
const uint32_t w = ammId[i];
programIdBytes.append(static_cast<char>(w & 0xff));
programIdBytes.append(static_cast<char>((w >> 8) & 0xff));
programIdBytes.append(static_cast<char>((w >> 16) & 0xff));
programIdBytes.append(static_cast<char>((w >> 24) & 0xff));
}
const QString programIdHex = QString::fromLatin1(programIdBytes.toHex());
AMM_DBG() << "[amm-debug] swapExactInput: program_id_hex=" << programIdHex;
// `instruction` is a QVariant (bstr); `program_id_hex` is a plain QString
// (tstr) in the generated proxy — pass it directly, not QVariant-wrapped.
const QString resultJson = m_logos->logos_execution_zone.send_generic_public_transaction( const QString resultJson = m_logos->logos_execution_zone.send_generic_public_transaction(
accounts, signers, QVariant::fromValue(instructionBytes), QVariant::fromValue(elf), accounts, signers, QVariant::fromValue(instructionBytes), programIdHex);
QVariant::fromValue(QByteArray()));
AMM_DBG() << "[amm-debug] swapExactInput: send_generic_public_transaction ->" AMM_DBG() << "[amm-debug] swapExactInput: send_generic_public_transaction ->"
<< resultJson.size() << "chars; raw:" << resultJson.left(600); << resultJson.size() << "chars; raw:" << resultJson.left(600);

20
flake.lock generated
View File

@ -3413,17 +3413,17 @@
"rust-rapidsnark": "rust-rapidsnark" "rust-rapidsnark": "rust-rapidsnark"
}, },
"locked": { "locked": {
"lastModified": 1782310268, "lastModified": 1783788663,
"narHash": "sha256-tIIIO+V+w/C/KLtKnLIv8O8/GoJ4PzgJSWrlQCXJ2P4=", "narHash": "sha256-Tl3CDPFWdTgRliX03oUI92E4+8XbpsFpnwooNxM3q+s=",
"owner": "logos-blockchain", "owner": "logos-blockchain",
"repo": "lssa", "repo": "logos-execution-zone",
"rev": "fb8cbac40e0bda4f152415ff4f181cdc6bca6d4a", "rev": "415964d7f9043a1bfe28da8d0e8b3a6f64abb258",
"type": "github" "type": "github"
}, },
"original": { "original": {
"owner": "logos-blockchain", "owner": "logos-blockchain",
"repo": "lssa", "repo": "logos-execution-zone",
"rev": "fb8cbac40e0bda4f152415ff4f181cdc6bca6d4a", "rev": "415964d7f9043a1bfe28da8d0e8b3a6f64abb258",
"type": "github" "type": "github"
} }
}, },
@ -24345,16 +24345,16 @@
"nix-bundle-lgx": "nix-bundle-lgx_40" "nix-bundle-lgx": "nix-bundle-lgx_40"
}, },
"locked": { "locked": {
"lastModified": 1784205966, "lastModified": 1784294670,
"narHash": "sha256-9qDpsio9ms7sz2yf8umH2bZLL4esjNuNDWUvsPzdNYc=", "narHash": "sha256-4II7lLMMcvwKBprA8QMAvtYklQMwstlL3C9UuvT+2Ow=",
"owner": "gravityblast", "owner": "gravityblast",
"repo": "logos-execution-zone-module", "repo": "logos-execution-zone-module",
"rev": "a48fd1c7447885895c15a929b945b713cebf2032", "rev": "4513e21f08dbd69c8e75edd76da99a78d23b79f2",
"type": "github" "type": "github"
}, },
"original": { "original": {
"owner": "gravityblast", "owner": "gravityblast",
"ref": "fix/generic-tx-bstr-serialization", "ref": "fix/generic-tx-instruction-bstr",
"repo": "logos-execution-zone-module", "repo": "logos-execution-zone-module",
"type": "github" "type": "github"
} }

View File

@ -18,14 +18,25 @@
logos-module-builder.url = "github:logos-co/logos-module-builder"; logos-module-builder.url = "github:logos-co/logos-module-builder";
# Core wallet module (the LEZ wallet FFI Qt plugin). The input name must # Core wallet module (the LEZ wallet FFI Qt plugin). The input name must
# match the metadata.json `dependencies` entry so the builder can resolve # match the metadata.json `dependencies` entry so the builder can resolve it
# it as a module dependency. This rev pins LEZ (lssa) at fb8cbac4, which # as a module dependency.
# includes the macOS Metal-build fix, so no `--override-input` is needed. #
# Fork of logos-blockchain/logos-execution-zone-module @ d2e9400a with the # Fork of logos-blockchain/logos-execution-zone-module @ d70225ced with the
# QtRO serialization fix: send_generic_public_transaction's `instruction` and # QtRO serialization fix: send_generic_public_transaction's `instruction` uses
# `program_dependencies` use byte-string IPC types so the args survive the # a byte-string IPC type so the args survive the cross-process boundary (at
# cross-process boundary. See docs/amm-swap-qtro-serialization-bug.md. # d70225ced the API already takes program_id_hex instead of program_elf/deps).
logos_execution_zone.url = "github:gravityblast/logos-execution-zone-module?ref=fix/generic-tx-bstr-serialization"; # See docs/amm-swap-qtro-serialization-bug.md.
logos_execution_zone = {
url = "github:gravityblast/logos-execution-zone-module?ref=fix/generic-tx-instruction-bstr";
# Override the module's pinned LEZ monorepo (logos-execution-zone) to the
# SAME rev the target sequencer runs (415964d7): the wallet client and the
# sequencer must agree on the JSON-RPC API, or tx submission fails at
# runtime with `MethodNotFound`. 415964d7's wallet_ffi takes a program id
# for send_generic_public_transaction, matching the d70225ced module.
inputs.logos-execution-zone.url =
"github:logos-blockchain/logos-execution-zone?rev=415964d7f9043a1bfe28da8d0e8b3a6f64abb258";
};
}; };
outputs = outputs =