Skip to content

Commit c4cf9f3

Browse files
authored
Merge pull request #5215 from IntersectMBO/jj/dijkstra-txbody-guards
Add guards field to DijkstraTxBody
2 parents 02ed285 + 7bfee75 commit c4cf9f3

File tree

17 files changed

+111
-32
lines changed

17 files changed

+111
-32
lines changed

eras/alonzo/impl/CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
## 1.14.0.0
44

5+
* Add `reqSignerHashesTxBodyG`
56
* Add `mkScriptIntegrity`
67
* Changed the type of `hashScriptIntegrity`
78
* Add `ScriptIntegrityHashMismatch`

eras/alonzo/impl/src/Cardano/Ledger/Alonzo/Plutus/TxInfo.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -285,7 +285,7 @@ transTxBodyWithdrawals txBody = Map.toList (transWithdrawals (txBody ^. withdraw
285285
-- | Translate all required signers produced by `reqSignerHashesTxBodyL`s from within a
286286
-- `TxBody`
287287
transTxBodyReqSignerHashes :: AlonzoEraTxBody era => TxBody era -> [PV1.PubKeyHash]
288-
transTxBodyReqSignerHashes txBody = transKeyHash <$> Set.toList (txBody ^. reqSignerHashesTxBodyL)
288+
transTxBodyReqSignerHashes txBody = transKeyHash <$> Set.toList (txBody ^. reqSignerHashesTxBodyG)
289289

290290
-- | Translate all `TxDats`s from within `TxWits`
291291
transTxWitsDatums :: AlonzoEraTxWits era => TxWits era -> [(PV1.DatumHash, PV1.Datum)]

eras/alonzo/impl/src/Cardano/Ledger/Alonzo/TxBody.hs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
{-# LANGUAGE ConstraintKinds #-}
22
{-# LANGUAGE DataKinds #-}
3+
{-# LANGUAGE DefaultSignatures #-}
34
{-# LANGUAGE DeriveGeneric #-}
45
{-# LANGUAGE DerivingVia #-}
56
{-# LANGUAGE FlexibleContexts #-}
@@ -140,7 +141,13 @@ type ScriptIntegrityHash = SafeHash EraIndependentScriptIntegrity
140141
class (MaryEraTxBody era, AlonzoEraTxOut era) => AlonzoEraTxBody era where
141142
collateralInputsTxBodyL :: Lens' (TxBody era) (Set TxIn)
142143

143-
reqSignerHashesTxBodyL :: Lens' (TxBody era) (Set (KeyHash 'Witness))
144+
reqSignerHashesTxBodyL :: ProtVerAtMost era 11 => Lens' (TxBody era) (Set (KeyHash 'Witness))
145+
146+
reqSignerHashesTxBodyG ::
147+
SimpleGetter (TxBody era) (Set (KeyHash Witness))
148+
default reqSignerHashesTxBodyG ::
149+
ProtVerAtMost era 11 => SimpleGetter (TxBody era) (Set (KeyHash Witness))
150+
reqSignerHashesTxBodyG = reqSignerHashesTxBodyL
144151

145152
scriptIntegrityHashTxBodyL ::
146153
Lens' (TxBody era) (StrictMaybe ScriptIntegrityHash)

eras/alonzo/impl/src/Cardano/Ledger/Alonzo/UTxO.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -327,5 +327,5 @@ getAlonzoWitsVKeyNeeded ::
327327
Set.Set (KeyHash 'Witness)
328328
getAlonzoWitsVKeyNeeded certState utxo txBody =
329329
getShelleyWitsVKeyNeeded certState utxo txBody
330-
`Set.union` (txBody ^. reqSignerHashesTxBodyL)
330+
`Set.union` (txBody ^. reqSignerHashesTxBodyG)
331331
{-# INLINEABLE getAlonzoWitsVKeyNeeded #-}

eras/conway/impl/src/Cardano/Ledger/Conway/UTxO.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -178,7 +178,7 @@ getConwayWitsVKeyNeeded ::
178178
Set.Set (KeyHash 'Witness)
179179
getConwayWitsVKeyNeeded utxo txBody =
180180
getShelleyWitsVKeyNeededNoGov utxo txBody
181-
`Set.union` (txBody ^. reqSignerHashesTxBodyL)
181+
`Set.union` (txBody ^. reqSignerHashesTxBodyG)
182182
`Set.union` voterWitnesses txBody
183183

184184
voterWitnesses ::

eras/dijkstra/cardano-ledger-dijkstra.cabal

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,7 @@ library testlib
129129
build-depends:
130130
base,
131131
bytestring,
132+
cardano-data,
132133
cardano-ledger-alonzo:testlib,
133134
cardano-ledger-babbage:{cardano-ledger-babbage, testlib},
134135
cardano-ledger-binary,

eras/dijkstra/cddl-files/dijkstra.cddl

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ transaction_body =
139139
, ? 9 : mint
140140
, ? 11 : script_data_hash
141141
, ? 13 : nonempty_set<transaction_input>
142-
, ? 14 : required_signers
142+
, ? 14 : guards
143143
, ? 15 : network_id
144144
, ? 16 : transaction_output
145145
, ? 17 : coin
@@ -503,7 +503,7 @@ script_data_hash = hash32
503503

504504
nonempty_set<a0> = #6.258([+ a0])/ [+ a0]
505505

506-
required_signers = nonempty_set<addr_keyhash>
506+
guards = nonempty_set<addr_keyhash>/ nonempty_oset<credential>
507507

508508
network_id = 0/ 1
509509

eras/dijkstra/src/Cardano/Ledger/Dijkstra/TxBody.hs

Lines changed: 64 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
{-# LANGUAGE FlexibleContexts #-}
55
{-# LANGUAGE FlexibleInstances #-}
66
{-# LANGUAGE GeneralizedNewtypeDeriving #-}
7+
{-# LANGUAGE LambdaCase #-}
78
{-# LANGUAGE MultiParamTypeClasses #-}
89
{-# LANGUAGE PatternSynonyms #-}
910
{-# LANGUAGE RankNTypes #-}
@@ -12,10 +13,12 @@
1213
{-# LANGUAGE StandaloneDeriving #-}
1314
{-# LANGUAGE TypeApplications #-}
1415
{-# LANGUAGE TypeFamilies #-}
16+
{-# LANGUAGE UndecidableSuperClasses #-}
1517
{-# LANGUAGE ViewPatterns #-}
1618
{-# OPTIONS_GHC -Wno-orphans #-}
1719

1820
module Cardano.Ledger.Dijkstra.TxBody (
21+
DijkstraEraTxBody (..),
1922
TxBody (
2023
MkDijkstraTxBody,
2124
DijkstraTxBody,
@@ -29,15 +32,15 @@ module Cardano.Ledger.Dijkstra.TxBody (
2932
dtbWithdrawals,
3033
dtbTxfee,
3134
dtbVldt,
32-
dtbReqSignerHashes,
3335
dtbMint,
3436
dtbScriptIntegrityHash,
3537
dtbAdHash,
3638
dtbTxNetworkId,
3739
dtbVotingProcedures,
3840
dtbProposalProcedures,
3941
dtbCurrentTreasuryValue,
40-
dtbTreasuryDonation
42+
dtbTreasuryDonation,
43+
dtbGuards
4144
),
4245
upgradeProposals,
4346
upgradeGovAction,
@@ -53,10 +56,14 @@ import Cardano.Ledger.BaseTypes (Network, StrictMaybe (..), fromSMaybe)
5356
import Cardano.Ledger.Binary (
5457
Annotator,
5558
DecCBOR (..),
59+
Decoder,
5660
EncCBOR (..),
5761
Sized (..),
5862
ToCBOR,
63+
TokenType (..),
64+
liftST,
5965
mkSized,
66+
peekTokenType,
6067
)
6168
import Cardano.Ledger.Binary.Coders (
6269
Decode (..),
@@ -87,9 +94,11 @@ import Cardano.Ledger.Conway.TxBody (
8794
conwayRedeemerPointerInverse,
8895
)
8996
import Cardano.Ledger.Core (EraPParams (..))
97+
import Cardano.Ledger.Credential (Credential (..))
9098
import Cardano.Ledger.Dijkstra.Era (DijkstraEra)
9199
import Cardano.Ledger.Dijkstra.Scripts ()
92100
import Cardano.Ledger.Dijkstra.TxOut ()
101+
import Cardano.Ledger.Keys (HasKeyRole (..))
93102
import Cardano.Ledger.Mary.Value (MultiAsset, policies)
94103
import Cardano.Ledger.MemoBytes (
95104
EqRaw,
@@ -106,11 +115,14 @@ import Cardano.Ledger.TxIn (TxIn)
106115
import Cardano.Ledger.Val (Val (..))
107116
import Control.DeepSeq (NFData)
108117
import Data.Coerce (coerce)
118+
import Data.OSet.Strict (OSet, decodeOSet)
109119
import qualified Data.OSet.Strict as OSet
120+
import Data.STRef (newSTRef, readSTRef, writeSTRef)
110121
import Data.Sequence.Strict (StrictSeq)
111-
import Data.Set (Set)
122+
import Data.Set (Set, foldr')
123+
import qualified Data.Set as Set
112124
import GHC.Generics (Generic)
113-
import Lens.Micro (to, (^.))
125+
import Lens.Micro (Lens', to, (^.))
114126
import NoThunks.Class (NoThunks)
115127

116128
data DijkstraTxBodyRaw = DijkstraTxBodyRaw
@@ -124,7 +136,7 @@ data DijkstraTxBodyRaw = DijkstraTxBodyRaw
124136
, dtbrWithdrawals :: !Withdrawals
125137
, dtbrFee :: !Coin
126138
, dtbrVldt :: !ValidityInterval
127-
, dtbrReqSignerHashes :: !(Set (KeyHash 'Witness))
139+
, dtbrGuards :: !(OSet (Credential Guard))
128140
, dtbrMint :: !MultiAsset
129141
, dtbrScriptIntegrityHash :: !(StrictMaybe ScriptIntegrityHash)
130142
, dtbrAuxDataHash :: !(StrictMaybe TxAuxDataHash)
@@ -217,11 +229,9 @@ instance DecCBOR DijkstraTxBodyRaw where
217229
(\x tx -> tx {dtbrCollateralInputs = x})
218230
From
219231
bodyFields 14 =
220-
fieldGuarded
221-
(emptyFailure "Required Signer Hashes" "non-empty")
222-
null
223-
(\x tx -> tx {dtbrReqSignerHashes = x})
224-
From
232+
ofield
233+
(\x tx -> tx {dtbrGuards = fromSMaybe mempty x})
234+
(D decodeGuards)
225235
bodyFields 15 = ofield (\x tx -> tx {dtbrNetworkId = x}) From
226236
bodyFields 16 = ofield (\x tx -> tx {dtbrCollateralReturn = x}) From
227237
bodyFields 17 = ofield (\x tx -> tx {dtbrTotalCollateral = x}) From
@@ -278,7 +288,7 @@ encodeTxBodyRaw DijkstraTxBodyRaw {..} =
278288
!> Omit OSet.null (Key 4 (To dtbrCerts))
279289
!> Omit (null . unWithdrawals) (Key 5 (To dtbrWithdrawals))
280290
!> encodeKeyedStrictMaybe 8 bot
281-
!> Omit null (Key 14 (To dtbrReqSignerHashes))
291+
!> Omit null (Key 14 (To dtbrGuards))
282292
!> Omit (== mempty) (Key 9 (To dtbrMint))
283293
!> encodeKeyedStrictMaybe 11 dtbrScriptIntegrityHash
284294
!> encodeKeyedStrictMaybe 7 dtbrAuxDataHash
@@ -310,7 +320,7 @@ pattern DijkstraTxBody ::
310320
Withdrawals ->
311321
Coin ->
312322
ValidityInterval ->
313-
Set (KeyHash 'Witness) ->
323+
OSet (Credential Guard) ->
314324
MultiAsset ->
315325
StrictMaybe ScriptIntegrityHash ->
316326
StrictMaybe TxAuxDataHash ->
@@ -331,7 +341,7 @@ pattern DijkstraTxBody
331341
, dtbWithdrawals
332342
, dtbTxfee
333343
, dtbVldt
334-
, dtbReqSignerHashes
344+
, dtbGuards
335345
, dtbMint
336346
, dtbScriptIntegrityHash
337347
, dtbAdHash
@@ -353,7 +363,7 @@ pattern DijkstraTxBody
353363
, dtbrWithdrawals = dtbWithdrawals
354364
, dtbrFee = dtbTxfee
355365
, dtbrVldt = dtbVldt
356-
, dtbrReqSignerHashes = dtbReqSignerHashes
366+
, dtbrGuards = dtbGuards
357367
, dtbrMint = dtbMint
358368
, dtbrScriptIntegrityHash = dtbScriptIntegrityHash
359369
, dtbrAuxDataHash = dtbAdHash
@@ -376,7 +386,7 @@ pattern DijkstraTxBody
376386
withdrawalsX
377387
txfeeX
378388
vldtX
379-
reqSignerHashesX
389+
guards
380390
mintX
381391
scriptIntegrityHashX
382392
adHashX
@@ -397,7 +407,7 @@ pattern DijkstraTxBody
397407
withdrawalsX
398408
txfeeX
399409
vldtX
400-
reqSignerHashesX
410+
guards
401411
mintX
402412
scriptIntegrityHashX
403413
adHashX
@@ -514,11 +524,15 @@ instance AlonzoEraTxBody DijkstraEra where
514524
\txb x -> txb {dtbrCollateralInputs = x}
515525
{-# INLINE collateralInputsTxBodyL #-}
516526

517-
reqSignerHashesTxBodyL =
518-
lensMemoRawType @DijkstraEra dtbrReqSignerHashes $
519-
\txb x -> txb {dtbrReqSignerHashes = x}
527+
reqSignerHashesTxBodyL = notSupportedInThisEraL
520528
{-# INLINE reqSignerHashesTxBodyL #-}
521529

530+
reqSignerHashesTxBodyG = guardsTxBodyL . to (foldr' insertKeyHash mempty . OSet.toSet)
531+
where
532+
insertKeyHash (KeyHashObj kh) = Set.insert $ coerceKeyRole kh
533+
insertKeyHash (ScriptHashObj _) = id
534+
{-# INLINE reqSignerHashesTxBodyG #-}
535+
522536
scriptIntegrityHashTxBodyL =
523537
lensMemoRawType @DijkstraEra dtbrScriptIntegrityHash $
524538
\txb x -> txb {dtbrScriptIntegrityHash = x}
@@ -577,3 +591,34 @@ instance ConwayEraTxBody DijkstraEra where
577591
lensMemoRawType @DijkstraEra dtbrTreasuryDonation $
578592
\txb x -> txb {dtbrTreasuryDonation = x}
579593
{-# INLINE treasuryDonationTxBodyL #-}
594+
595+
class ConwayEraTxBody era => DijkstraEraTxBody era where
596+
guardsTxBodyL :: Lens' (TxBody era) (OSet (Credential Guard))
597+
598+
instance DijkstraEraTxBody DijkstraEra where
599+
{-# INLINE guardsTxBodyL #-}
600+
guardsTxBodyL =
601+
lensMemoRawType @DijkstraEra dtbrGuards $
602+
\txb x -> txb {dtbrGuards = x}
603+
604+
-- | Decoder for decoding guards in a backwards-compatible manner. It peeks at
605+
-- the first element and if it's a credential, it decodes the rest of the
606+
-- elements as credentials. If the first element is a plain keyhash, it will
607+
-- decode rest of the elements as keyhashes.
608+
decodeGuards :: Decoder s (OSet (Credential Guard))
609+
decodeGuards = do
610+
elementsAreCredentials <- liftST $ newSTRef Nothing
611+
let
612+
decodeElement = do
613+
liftST (readSTRef elementsAreCredentials) >>= \case
614+
Nothing -> do
615+
tokenType <- peekTokenType
616+
liftST . writeSTRef elementsAreCredentials . Just $ case tokenType of
617+
TypeListLen -> True
618+
TypeListLen64 -> True
619+
TypeListLenIndef -> True
620+
_ -> False
621+
decodeElement
622+
Just True -> decCBOR
623+
Just False -> KeyHashObj <$> decCBOR
624+
decodeOSet decodeElement

eras/dijkstra/testlib/Test/Cardano/Ledger/Dijkstra/CDDL.hs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -147,7 +147,7 @@ transaction_body =
147147
, opt (idx 9 ==> mint)
148148
, opt (idx 11 ==> script_data_hash)
149149
, opt (idx 13 ==> nonempty_set transaction_input)
150-
, opt (idx 14 ==> required_signers)
150+
, opt (idx 14 ==> guards)
151151
, opt (idx 15 ==> network_id)
152152
, opt (idx 16 ==> transaction_output)
153153
, opt (idx 17 ==> coin)
@@ -158,6 +158,12 @@ transaction_body =
158158
, opt (idx 22 ==> positive_coin)
159159
]
160160

161+
guards :: Rule
162+
guards =
163+
"guards"
164+
=:= nonempty_set addr_keyhash
165+
/ nonempty_oset credential
166+
161167
proposal_procedure :: Rule
162168
proposal_procedure =
163169
"proposal_procedure"

eras/dijkstra/testlib/Test/Cardano/Ledger/Dijkstra/Examples.hs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,12 +27,14 @@ import Cardano.Ledger.Plutus.Data (
2727
import Cardano.Ledger.Plutus.Language (Language (..))
2828
import Cardano.Ledger.Shelley.API (
2929
ApplyTxError (..),
30+
Credential (..),
3031
RewardAccount (..),
3132
TxId (..),
3233
)
3334
import Cardano.Ledger.TxIn (mkTxInPartial)
3435
import Control.State.Transition.Extended (Embed (..))
3536
import qualified Data.Map.Strict as Map
37+
import qualified Data.OSet.Strict as OSet
3638
import qualified Data.Sequence.Strict as StrictSeq
3739
import qualified Data.Set as Set
3840
import Test.Cardano.Ledger.Alonzo.Arbitrary (alwaysSucceeds)
@@ -54,6 +56,7 @@ import Test.Cardano.Ledger.Shelley.Examples (
5456
exampleStakeKey,
5557
keyToCredential,
5658
mkKeyHash,
59+
mkScriptHash,
5760
)
5861

5962
ledgerExamples :: LedgerExamples DijkstraEra
@@ -96,7 +99,7 @@ exampleTxBodyDijkstra =
9699
)
97100
(Coin 999) -- txfee
98101
(ValidityInterval (SJust (SlotNo 2)) (SJust (SlotNo 4))) -- txvldt
99-
(Set.singleton $ mkKeyHash 212) -- reqSignerHashes
102+
(OSet.fromList [KeyHashObj $ mkKeyHash 212, ScriptHashObj $ mkScriptHash 213]) -- guards
100103
exampleMultiAsset -- mint
101104
(SJust $ mkDummySafeHash 42) -- scriptIntegrityHash
102105
(SJust . TxAuxDataHash $ mkDummySafeHash 42) -- adHash

0 commit comments

Comments
 (0)