Editorial illustration for Kaspa vProgs Authenticated State Trees: Unified ZK Batch Verification
Kaspa vProgs Authenticated State Trees: Unified ZK Batch Verification
March 22, 2026
Editorial illustration for Rusty Kaspa musl Toolchain: Portable Linux Builds Explained
Rusty Kaspa musl Toolchain: Portable Linux Builds Explained
March 27, 2026

Kaspa Transaction Introspection: New Opcodes for Covenant Fields


KaspaBuy
July 16, 2026

Kaspa transaction introspection expanded in Rusty Kaspa PR #920 through two covenant-output opcodes: OpOutputCovenantId and OpOutputAuthorizingInput. Scripts could query an output’s covenant identity and the input authorizing it, while defined sentinel values handled outputs without covenants. The merge targeted covpp-reset2, so it was development evidence, not mainnet activation.

Key takeaways

  • OpOutputCovenantId at opcode 0xd5 returns an indexed output’s covenant ID or a zero hash when no covenant exists.
  • OpOutputAuthorizingInput at 0xd6 returns the authorizing input index or -1 when the output has no covenant.
  • Existing OpInputCovenantId behavior changed from a Boolean false value to a zero hash for consistent stack types.
  • Both new operations require covenant engine flags and a transaction-input script context; invalid indexes still fail.
  • The two-commit PR merged into a Covenant++ development branch and did not prove that the opcodes were active on mainnet at that date.

What did Kaspa transaction introspection PR #920 change?

The official Rusty Kaspa PR #920 merged on March 25, 2026 with 103 additions, 24 deletions, and four changed files. Its base was covpp-reset2, not master. Most implementation work touched the transaction-script opcode engine and covenant test vectors.

Transaction introspection lets a script inspect selected fields of the transaction attempting to spend a UTXO. In a covenant design, that matters because the current script may need to constrain what the next outputs contain and how those outputs remain linked to authorized inputs.

PR #920 focused on metadata specific to covenant outputs. It did not add a general-purpose virtual machine, arbitrary network access, or hidden mutable storage.

How did OpOutputCovenantId work?

OpOutputCovenantId uses byte 0xd5. The script pushes an output index, the engine checks that the index is non-negative and in range, and the operation returns that output’s 32-byte covenant ID. If the output has no covenant, it pushes the all-zero hash.

A stable return type matters for composability. Scripts can compare a 32-byte result with an expected covenant ID without first handling a Boolean alternative. The zero hash is a sentinel for absence, not a valid assertion that a covenant with that identity was authorized.

The tests covered outputs with covenant IDs, absent covenants, and out-of-bounds access. Passing those cases documents intended behavior, but application scripts still need to distinguish absence explicitly and avoid accidentally accepting the sentinel.

What did OpOutputAuthorizingInput reveal?

OpOutputAuthorizingInput uses byte 0xd6. Given an output index, it returns the index of the transaction input recorded as authorizing that output’s covenant. When the output has no covenant, it returns -1.

This relationship can help a covenant script enforce continuation rules. For example, an application may need to show that a newly created state output is authorized by the input carrying the previous state. The opcode exposes the recorded relationship; it does not independently determine whether the surrounding application transition is economically or logically correct.

The engine rejects invalid output indexes and non-transaction-input script sources. Those errors are safety boundaries, not optional user-interface behavior.

Why was OpInputCovenantId made type-consistent?

Before PR #920, an input without a covenant ID pushed false. After the merge, it pushed the zero hash, matching the new output query. A script comparing covenant identities can now expect hash-shaped data for both input and output absence.

Type consistency reduces branching and surprise, but it can break assumptions in experimental scripts written against the earlier development behavior. Developers following the branch needed to update fixtures and explicitly test no-covenant paths. The merge’s JSON test vectors did exactly that by comparing absent input and output IDs with 32 zero bytes.

This low-level behavior is adjacent to the broader vProgs authenticated-state prototype, but the two systems solve different problems: script introspection constrains a UTXO spend, while an authenticated state tree commits to application state.

When were the new opcodes enabled?

The implementation checked vm.flags.covenants_enabled. Without that flag, the byte codes remained invalid. It also required ScriptSource::TxInput, because the opcodes inspect the transaction being authorized from an input’s execution context.

That gating is essential when adding script semantics. Reinterpreting formerly invalid bytes without coordinated activation can split validation behavior between node versions. A merge into covpp-reset2 showed code integration and tests in the development line, not a coordinated mainnet activation event.

Developers could use the SilverScript debugger overview to understand inspection workflows, but high-level tooling cannot override the node engine’s activation flags or consensus rules.

What could developers build, and what remained risky?

Output covenant identities and authorizing-input indexes are building blocks for state-continuation rules, controlled assets, vault-like policies, and other transaction graphs. They make relationships inspectable; they do not provide safe application logic automatically.

A contract can still contain index confusion, sentinel-value mistakes, unintended alternate spend paths, denial-of-service costs, or faulty authorization conditions. Developers should test every index boundary, missing-covenant case, multi-input arrangement, and state transition. Independent review is especially important when a script controls valuable UTXOs.

Did PR #920 change the roadmap or KAS price?

The merge demonstrated progress on covenant transaction fields in a development branch. It did not announce a mainnet date, a final opcode set, an audit result, application demand, or network usage. No price target or investment conclusion can be derived from four changed files.

Frequently asked questions

What is transaction introspection?

It is a script capability for reading defined fields of the transaction being validated. The script can then enforce conditions on inputs, outputs, amounts, identities, or other exposed data.

Why return a zero hash instead of false?

The zero hash keeps covenant-ID query results type-consistent. Scripts still must treat it as an absence sentinel rather than an ordinary covenant identity.

Was 0xd6 an authorizing signature check?

No. It returned an authorizing input index recorded for the covenant output. The script’s complete authorization rules still had to validate the relevant transaction conditions.

Were these opcodes live on mainnet on March 25, 2026?

PR #920 alone does not establish that. It merged into covpp-reset2, and the code required covenant activation flags.

Source and verification note

This article is based on merged kaspanet/rusty-kaspa PR #920, including its merge branch, diff, opcode implementation, and covenant test vectors. The GitHub record establishes two commits, four changed files, sentinel values, context checks, and branch-level activation gating. It does not establish mainnet activation, final compatibility, an independent audit, production applications, adoption, or a KAS price effect.

Related Posts

Kaspa Transaction Introspection: New Opcodes for Covenant Fields
This website uses cookies to improve your experience. By using this website you agree to our Data Protection Policy.
Read more