Skip to content

Commit

Permalink
conway: add tx body items
Browse files Browse the repository at this point in the history
  • Loading branch information
janmazak committed Dec 20, 2023
1 parent 0535a18 commit 4d56f43
Show file tree
Hide file tree
Showing 26 changed files with 2,609 additions and 534 deletions.
1 change: 1 addition & 0 deletions .cspell.json
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@
"deregistration",
"DEVEL",
"dpkg",
"DREP",
"endians",
"financials",
"hwsfile",
Expand Down
15 changes: 15 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,21 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/)
and this project adheres to [Semantic Versioning](http://semver.org/).


## [7.0.0](TBD) - [TBD]

Support for Conway era

### Added

- export of Conway-era keys (DReps, Constitutional Committee Hot and Cold keys)
- Conway era transaction body items (new certificates, voting procedures, treasury, donation)
- support for reduced features on Nano S (since Ledger app v7, due to memory limits)

### Changed

- names of credential types (e.g. StakeCredentialParamsType -> CredentialParamsType)


## [6.0.0](TBD) - [TBD]

Support for CIP0036 voting
Expand Down
8 changes: 4 additions & 4 deletions example-node/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import SpeculosTransport from '@ledgerhq/hw-transport-node-speculos'

import {
Certificate,
StakeCredentialParamsType,
CredentialParamsType,
TxInput,
TxOutput,
Withdrawal,
Expand Down Expand Up @@ -216,7 +216,7 @@ const signTransaction = async (appAda: Ada) => {
type: CertificateType.STAKE_REGISTRATION,
params: {
stakeCredential: {
type: StakeCredentialParamsType.KEY_PATH,
type: CredentialParamsType.KEY_PATH,
keyPath: [1852 + HARDENED, 1815 + HARDENED, 0 + HARDENED, 2, 0],
},
},
Expand All @@ -225,7 +225,7 @@ const signTransaction = async (appAda: Ada) => {
type: CertificateType.STAKE_DELEGATION,
params: {
stakeCredential: {
type: StakeCredentialParamsType.KEY_PATH,
type: CredentialParamsType.KEY_PATH,
keyPath: [1852 + HARDENED, 1815 + HARDENED, 0 + HARDENED, 2, 0],
},
poolKeyHashHex:
Expand All @@ -237,7 +237,7 @@ const signTransaction = async (appAda: Ada) => {
const withdrawals: Withdrawal[] = [
{
stakeCredential: {
type: StakeCredentialParamsType.KEY_PATH,
type: CredentialParamsType.KEY_PATH,
keyPath: [1852 + HARDENED, 1815 + HARDENED, 0 + HARDENED, 2, 0],
},
amount: '1000',
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@cardano-foundation/ledgerjs-hw-app-cardano",
"version": "6.0.0",
"version": "7.0.0",
"files": [
"dist"
],
Expand Down
50 changes: 38 additions & 12 deletions src/errors/invalidDataReason.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,12 +57,17 @@ export enum InvalidDataReason {

CERTIFICATES_NOT_ARRAY = 'certificates not an array',

CERTIFICATE_INVALID_TYPE = 'invalid certificate type',
CERTIFICATE_INVALID_PATH = 'one of the certificates contains an invalid path',
CERTIFICATE_INVALID_SCRIPT_HASH = 'one of the certificates contains an invalid script hash',
CERTIFICATE_INVALID_STAKE_CREDENTIAL = 'one of the certificates contains both a path and a scripthash or neither',
CERTIFICATE_INVALID_STAKE_CREDENTIAL = 'one of the certificates contains an invalid stake credential',
CERTIFICATE_INVALID_COMMITTEE_CREDENTIAL = 'one of the certificates contains invalid constitutional committee credential',
CERTIFICATE_INVALID_DREP_CREDENTIAL = 'one of the certificates contains an invalid DRep credential',
CERTIFICATE_INVALID_POOL_KEY_HASH = 'one of the certificates contains an invalid pool key hash',
CERTIFICATE_SUPERFLUOUS_POOL_KEY_HASH = 'superfluous pool key hash in a certificate',
CERTIFICATE_INVALID_TYPE = 'invalid certificate type',
CERTIFICATE_INVALID_DEPOSIT = 'one of the certificates contains an invalid deposit',
CERTIFICATE_INVALID_DREP = 'one of the certificates contains an invalid DRep',
ANCHOR_INVALID_URL = 'anchor with an invalid URL',
ANCHOR_INVALID_HASH = 'anchor with an invalid data hash',

POOL_REGISTRATION_INVALID_VRF_KEY_HASH = 'invalid vrf key hash in a pool registration certificate',
POOL_REGISTRATION_INVALID_PLEDGE = 'invalid pledge in a pool registration certificate',
Expand Down Expand Up @@ -140,56 +145,77 @@ export enum InvalidDataReason {

REFERENCE_INPUTS_NOT_ARRAY = 'reference inputs not an array',

VOTING_PROCEDURES_NOT_ARRAY = 'voting procedures not an array',
VOTER_VOTES_NOT_ARRAY = "voter's votes not an array",
VOTER_INVALID = 'invalid voter in voting procedures',
GOV_ACTION_ID_INVALID_TX_HASH = 'invalid governance action id tx hash',
GOV_ACTION_ID_INVALID_INDEX = 'invalid governance action id index',
VOTING_PROCEDURES_INVALID_NUMBER_OF_VOTERS = 'there must be exactly 1 voter in voting procedures',
VOTING_PROCEDURES_INVALID_NUMBER_OF_VOTES = 'there must be exactly 1 voting procedure per voter',

TREASURY_NOT_VALID = 'treasury amount not valid',

DONATION_NOT_VALID = 'treasury donation not valid',

SIGN_MODE_UNKNOWN = 'unknown signing mode',

SIGN_MODE_ORDINARY__POOL_REGISTRATION_NOT_ALLOWED = 'pool registration not allowed in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__CERTIFICATE_STAKE_CREDENTIAL_ONLY_AS_PATH = 'certificate stake credential must be given as a staking path in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__CERTIFICATE_COMMITTEE_COLD_CREDENTIAL_ONLY_AS_PATH = 'certificate constitutional committee cold credential must be given as a path in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__CERTIFICATE_DREP_CREDENTIAL_ONLY_AS_PATH = 'certificate DRep credential must be given as a path in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__WITHDRAWAL_ONLY_AS_PATH = 'withdrawal must be given as a path in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__COLLATERAL_INPUTS_NOT_ALLOWED = 'collateral inputs not allowed in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__COLLATERAL_OUTPUT_NOT_ALLOWED = 'collateral output not allowed in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__TOTAL_COLLATERAL_NOT_ALLOWED = 'total collateral not allowed in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__REFERENCE_INPUTS_NOT_ALLOWED = 'reference inputs not allowed in TransactionSigningMode.ORDINARY_TRANSACTION',
SIGN_MODE_ORDINARY__VOTER_ONLY_AS_PATH = 'voter credential in voting procedures must be given as a path in TransactionSigningMode.ORDINARY_TRANSACTION',

SIGN_MODE_MULTISIG__POOL_REGISTRATION_NOT_ALLOWED = 'pool registration not allowed in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__POOL_RETIREMENT_NOT_ALLOWED = 'pool retirement not allowed in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__DEVICE_OWNED_ADDRESS_NOT_ALLOWED = 'outputs given by path not allowed in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__CERTIFICATE_STAKE_CREDENTIAL_ONLY_AS_SCRIPT = 'certificate stake credential must be given as a script hash in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__WITHDRAWAL_ONLY_AS_SCRIPT = 'withdrawal must be given as a script hash in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__CERTIFICATE_CREDENTIAL_ONLY_AS_SCRIPT = 'certificate credential must be a script hash in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__WITHDRAWAL_ONLY_AS_SCRIPT = 'withdrawal must be a script hash in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__COLLATERAL_INPUTS_NOT_ALLOWED = 'collateral inputs not allowed in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__COLLATERAL_OUTPUT_NOT_ALLOWED = 'collateral output not allowed in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__TOTAL_COLLATERAL_NOT_ALLOWED = 'total collateral not allowed in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__REFERENCE_INPUTS_NOT_ALLOWED = 'reference inputs not allowed in TransactionSigningMode.MULTISIG_TRANSACTION',
SIGN_MODE_MULTISIG__VOTER_ONLY_AS_SCRIPT = 'voter credential in voting procedures must be a script hash in TransactionSigningMode.MULTISIG_TRANSACTION',

SIGN_MODE_POOL_OWNER__INPUT_WITH_PATH_NOT_ALLOWED = 'inputs with path not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__DEVICE_OWNED_ADDRESS_NOT_ALLOWED = 'outputs given by path are not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__DATUM_NOT_ALLOWED = 'datum in outputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__REFERENCE_SCRIPT_NOT_ALLOWED = 'reference script in outputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__INPUT_WITH_PATH_NOT_ALLOWED = 'inputs with path not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__SINGLE_POOL_REG_CERTIFICATE_REQUIRED = 'single pool registration certificate is expected in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__THIRD_PARTY_POOL_KEY_REQUIRED = 'third party pool key is required in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__SINGLE_DEVICE_OWNER_REQUIRED = 'single device-owned pool owner is expected in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__WITHDRAWALS_NOT_ALLOWED = 'withdrawals not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__MINT_NOT_ALLOWED = 'mint not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__SCRIPT_DATA_HASH_NOT_ALLOWED = 'script data hash not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__COLLATERAL_INPUTS_NOT_ALLOWED = 'collateral inputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__COLLATERAL_OUTPUT_NOT_ALLOWED = 'reference inputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__TOTAL_COLLATERAL_NOT_ALLOWED = 'total collateral not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__REQUIRED_SIGNERS_NOT_ALLOWED = 'required signers not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__THIRD_PARTY_POOL_KEY_REQUIRED = 'third party pool key is required in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',

SIGN_MODE_POOL_OWNER__COLLATERAL_OUTPUT_NOT_ALLOWED = 'reference inputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__REFERENCE_INPUTS_NOT_ALLOWED = 'reference inputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__VOTING_PROCEDURES_NOT_ALLOWED = 'voting procedures not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__TREASURY_NOT_ALLOWED = 'treasury amount not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',
SIGN_MODE_POOL_OWNER__DONATION_NOT_ALLOWED = 'treasury donation not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OWNER',

SIGN_MODE_POOL_OPERATOR__DATUM_NOT_ALLOWED = 'datum in outputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__REFERENCE_SCRIPT_NOT_ALLOWED = 'reference script in outputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__SINGLE_POOL_REG_CERTIFICATE_REQUIRED = 'single pool registration certificate is expected in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__DEVICE_OWNED_POOL_KEY_REQUIRED = 'device owned pool key is required in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__DEVICE_OWNED_POOL_OWNER_NOT_ALLOWED = 'device-owned pool owner not expected in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__WITHDRAWALS_NOT_ALLOWED = 'withdrawals not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__MINT_NOT_ALLOWED = 'mint not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__SCRIPT_DATA_HASH_NOT_ALLOWED = 'script data hash not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__COLLATERAL_INPUTS_NOT_ALLOWED = 'collateral inputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__REQUIRED_SIGNERS_NOT_ALLOWED = 'required signers not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__DATUM_NOT_ALLOWED = 'datum in outputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__REFERENCE_SCRIPT_NOT_ALLOWED = 'reference script in outputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__COLLATERAL_OUTPUT_NOT_ALLOWED = 'collateral output not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__TOTAL_COLLATERAL_NOT_ALLOWED = 'total collateral not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__REQUIRED_SIGNERS_NOT_ALLOWED = 'required signers not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__REFERENCE_INPUTS_NOT_ALLOWED = 'reference inputs not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__VOTING_PROCEDURES_NOT_ALLOWED = 'voting procedures not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__TREASURY_NOT_ALLOWED = 'treasury amount not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',
SIGN_MODE_POOL_OPERATOR__DONATION_NOT_ALLOWED = 'treasury donation not allowed in TransactionSigningMode.POOL_REGISTRATION_AS_OPERATOR',

SIGN_MODE_PLUTUS__DEVICE_OWNED_ADDRESS_NOT_ALLOWED = 'outputs given by path not allowed in TransactionSigningMode.PLUTUS_TRANSACTION',
SIGN_MODE_PLUTUS__POOL_REGISTRATION_NOT_ALLOWED = 'pool registration not allowed in TransactionSigningMode.PLUTUS_TRANSACTION',
Expand Down
22 changes: 13 additions & 9 deletions src/interactions/getVersion.ts
Original file line number Diff line number Diff line change
Expand Up @@ -63,34 +63,37 @@ export function getCompatibility(version: Version): DeviceCompatibility {
// We restrict forward compatibility only to backward-compatible semver changes
const v2_2 =
isLedgerAppVersionAtLeast(version, 2, 2) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v2_3 =
isLedgerAppVersionAtLeast(version, 2, 3) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v2_4 =
isLedgerAppVersionAtLeast(version, 2, 4) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v3_0 =
isLedgerAppVersionAtLeast(version, 3, 0) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v4_0 =
isLedgerAppVersionAtLeast(version, 4, 0) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v4_1 =
isLedgerAppVersionAtLeast(version, 4, 1) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v5_0 =
isLedgerAppVersionAtLeast(version, 5, 0) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v6_0 =
isLedgerAppVersionAtLeast(version, 6, 0) &&
isLedgerAppVersionAtMost(version, 6, Infinity)
isLedgerAppVersionAtMost(version, 7, Infinity)
const v7_0 =
isLedgerAppVersionAtLeast(version, 7, 0) &&
isLedgerAppVersionAtMost(version, 7, Infinity)

const isAppXS = version.flags.isAppXS

return {
isCompatible: v2_2,
recommendedVersion: v2_2 ? null : '6.0',
recommendedVersion: v2_2 ? null : '7.0',
supportsByronAddressDerivation: v2_2 && !isAppXS,
supportsMary: v2_2,
supportsCatalystRegistration: v2_3, // CIP-15
Expand All @@ -106,6 +109,7 @@ export function getCompatibility(version: Version): DeviceCompatibility {
supportsReqSignersInOrdinaryTx: v4_1,
supportsBabbage: v5_0,
supportsCIP36Vote: v6_0,
supportsConway: v7_0,
}
}

Expand Down
9 changes: 5 additions & 4 deletions src/interactions/serialization/poolRegistrationCertificate.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import {
uint16_to_buf,
uint32_to_buf,
uint64_to_buf,
serializeCoin,
} from '../../utils/serialize'

const SignTxIncluded = Object.freeze({
Expand All @@ -43,8 +44,8 @@ export function serializePoolInitialParamsLegacy(
// eslint-disable-next-line @typescript-eslint/no-use-before-define
serializePoolKeyLegacy(pool.poolKey),
hex_to_buf(pool.vrfHashHex),
uint64_to_buf(pool.pledge),
uint64_to_buf(pool.cost),
serializeCoin(pool.pledge),
serializeCoin(pool.cost),
uint64_to_buf(pool.margin.numerator),
uint64_to_buf(pool.margin.denominator),
// eslint-disable-next-line @typescript-eslint/no-use-before-define
Expand All @@ -56,8 +57,8 @@ export function serializePoolInitialParamsLegacy(

export function serializeFinancials(pool: ParsedPoolParams): Buffer {
return Buffer.concat([
uint64_to_buf(pool.pledge),
uint64_to_buf(pool.cost),
serializeCoin(pool.pledge),
serializeCoin(pool.cost),
uint64_to_buf(pool.margin.numerator),
uint64_to_buf(pool.margin.denominator),
])
Expand Down
Loading

0 comments on commit 4d56f43

Please sign in to comment.