1212{-# LANGUAGE StandaloneDeriving #-}
1313{-# LANGUAGE TypeApplications #-}
1414{-# LANGUAGE TypeFamilies #-}
15- {-# LANGUAGE TypeOperators #-}
1615{-# LANGUAGE UndecidableInstances #-}
1716{-# LANGUAGE UndecidableSuperClasses #-}
1817{-# LANGUAGE ViewPatterns #-}
1918{-# OPTIONS_GHC -Wno-orphans #-}
19+ {-# LANGUAGE BangPatterns #-}
2020
2121module Cardano.Ledger.Alonzo.TxOut (
2222 AlonzoEraTxOut (.. ),
@@ -82,11 +82,10 @@ import Data.Aeson (ToJSON (..), object, (.=))
8282import qualified Data.Aeson as Aeson (Value (Null , String ))
8383import Data.Bits
8484import Data.Maybe (fromMaybe )
85- import Data.Typeable (Proxy (.. ), (:~:) ( Refl ) )
85+ import Data.Typeable (Proxy (.. ))
8686import Data.Word
8787import GHC.Generics (Generic )
8888import GHC.Stack (HasCallStack )
89- import GHC.TypeLits
9089import Lens.Micro
9190import NoThunks.Class (InspectHeapNamed (.. ), NoThunks )
9291
@@ -114,19 +113,19 @@ data DataHash32
114113decodeAddress28 ::
115114 Credential 'Staking ->
116115 Addr28Extra ->
117- Maybe Addr
118- decodeAddress28 stakeRef (Addr28Extra a b c d) = do
119- Refl <- sameNat ( Proxy @ ( SizeHash ADDRHASH )) ( Proxy @ 28 )
120- let network = if d `testBit` 1 then Mainnet else Testnet
121- paymentCred =
122- if d `testBit` 0
123- then KeyHashObj (KeyHash addrHash)
124- else ScriptHashObj (ScriptHash addrHash)
125- addrHash :: Hash ADDRHASH a
126- addrHash =
127- hashFromPackedBytes $
128- PackedBytes28 a b c (fromIntegral (d `shiftR` 32 ))
129- pure $! Addr network paymentCred (StakeRefBase stakeRef)
116+ Addr
117+ decodeAddress28 stakeRef (Addr28Extra a b c d) =
118+ let
119+ network = if d `testBit` 1 then Mainnet else Testnet
120+ paymentCred =
121+ if d `testBit` 0
122+ then KeyHashObj (KeyHash addrHash)
123+ else ScriptHashObj (ScriptHash addrHash)
124+ addrHash :: Hash ADDRHASH a
125+ addrHash =
126+ hashFromPackedBytes $
127+ PackedBytes28 a b c (fromIntegral (d `shiftR` 32 ))
128+ in Addr network paymentCred (StakeRefBase stakeRef)
130129{-# INLINE decodeAddress28 #-}
131130
132131data AlonzoTxOut era
@@ -155,16 +154,11 @@ deriving instance Generic (AlonzoTxOut era)
155154instance NFData (AlonzoTxOut era ) where
156155 rnf = rwhnf
157156
158- addressErrorMsg :: String
159- addressErrorMsg = " Impossible: Compacted an address of non-standard size"
160- {-# NOINLINE addressErrorMsg #-}
161-
162157decodeDataHash32 ::
163158 DataHash32 ->
164- Maybe DataHash
159+ DataHash
165160decodeDataHash32 (DataHash32 a b c d) = do
166- Refl <- sameNat (Proxy @ (SizeHash HASH )) (Proxy @ 32 )
167- Just $! unsafeMakeSafeHash $ hashFromPackedBytes $ PackedBytes32 a b c d
161+ unsafeMakeSafeHash $ hashFromPackedBytes $ PackedBytes32 a b c d
168162
169163viewCompactTxOut ::
170164 Val (Value era ) =>
@@ -173,15 +167,15 @@ viewCompactTxOut ::
173167viewCompactTxOut txOut = case txOut of
174168 TxOutCompact' addr val -> (addr, val, SNothing )
175169 TxOutCompactDH' addr val dh -> (addr, val, SJust dh)
176- TxOut_AddrHash28_AdaOnly stakeRef addr28Extra adaVal
177- | Just addr <- decodeAddress28 stakeRef addr28Extra ->
178- (compactAddr addr, injectCompact adaVal, SNothing )
179- | otherwise -> error addressErrorMsg
180- TxOut_AddrHash28_AdaOnly_DataHash32 stakeRef addr28Extra adaVal dataHash32
181- | Just addr <- decodeAddress28 stakeRef addr28Extra
182- , Just dh <- decodeDataHash32 dataHash32 ->
183- (compactAddr addr, injectCompact adaVal, SJust dh)
184- | otherwise -> error addressErrorMsg
170+ TxOut_AddrHash28_AdaOnly stakeRef addr28Extra adaVal ->
171+ let
172+ ! addr = decodeAddress28 stakeRef addr28Extra
173+ in (compactAddr addr, injectCompact adaVal, SNothing )
174+ TxOut_AddrHash28_AdaOnly_DataHash32 stakeRef addr28Extra adaVal dataHash32 ->
175+ let
176+ ! addr = decodeAddress28 stakeRef addr28Extra
177+ ! dh = decodeDataHash32 dataHash32
178+ in (compactAddr addr, injectCompact adaVal, SJust dh)
185179
186180viewTxOut ::
187181 Val (Value era ) =>
@@ -195,15 +189,14 @@ viewTxOut (TxOutCompactDH' bs c dh) = (addr, val, SJust dh)
195189 where
196190 addr = decompactAddr bs
197191 val = fromCompact c
198- viewTxOut (TxOut_AddrHash28_AdaOnly stakeRef addr28Extra adaVal)
199- | Just addr <- decodeAddress28 stakeRef addr28Extra =
200- (addr, inject (fromCompact adaVal), SNothing )
201- viewTxOut (TxOut_AddrHash28_AdaOnly_DataHash32 stakeRef addr28Extra adaVal dataHash32)
202- | Just addr <- decodeAddress28 stakeRef addr28Extra
203- , Just dh <- decodeDataHash32 dataHash32 =
204- (addr, inject (fromCompact adaVal), SJust dh)
205- viewTxOut TxOut_AddrHash28_AdaOnly {} = error addressErrorMsg
206- viewTxOut TxOut_AddrHash28_AdaOnly_DataHash32 {} = error addressErrorMsg
192+ viewTxOut (TxOut_AddrHash28_AdaOnly stakeRef addr28Extra adaVal) =
193+ let ! addr = decodeAddress28 stakeRef addr28Extra
194+ in (addr, inject (fromCompact adaVal), SNothing )
195+ viewTxOut (TxOut_AddrHash28_AdaOnly_DataHash32 stakeRef addr28Extra adaVal dataHash32) =
196+ let
197+ ! addr = decodeAddress28 stakeRef addr28Extra
198+ ! dh = decodeDataHash32 dataHash32
199+ in (addr, inject (fromCompact adaVal), SJust dh)
207200
208201instance (Era era , Val (Value era )) => Show (AlonzoTxOut era ) where
209202 show = show . viewTxOut -- FIXME: showing tuple is ugly
@@ -213,7 +206,7 @@ deriving via InspectHeapNamed "AlonzoTxOut" (AlonzoTxOut era) instance NoThunks
213206encodeAddress28 ::
214207 Network ->
215208 PaymentCredential ->
216- Maybe ( SizeHash ADDRHASH :~: 28 , Addr28Extra )
209+ Addr28Extra
217210encodeAddress28 network paymentCred = do
218211 let networkBit, payCredTypeBit :: Word64
219212 networkBit =
@@ -226,26 +219,28 @@ encodeAddress28 network paymentCred = do
226219 ScriptHashObj {} -> 0
227220 encodeAddr ::
228221 Hash ADDRHASH a ->
229- Maybe ( SizeHash ADDRHASH :~: 28 , Addr28Extra )
222+ Addr28Extra
230223 encodeAddr h = do
231- refl@ Refl <- sameNat (Proxy @ (SizeHash ADDRHASH )) (Proxy @ 28 )
232224 case hashToPackedBytes h of
233225 PackedBytes28 a b c d ->
234226 let d' = (fromIntegral d `shiftL` 32 ) .|. networkBit .|. payCredTypeBit
235- in Just (refl, Addr28Extra a b c d')
236- _ -> Nothing
227+ in Addr28Extra a b c d'
228+ _ ->
229+ -- This case should never match, but if it does, we output garbage
230+ Addr28Extra 0xaa 0xaa 0xaa 0xaa
237231 case paymentCred of
238232 KeyHashObj (KeyHash addrHash) -> encodeAddr addrHash
239233 ScriptHashObj (ScriptHash addrHash) -> encodeAddr addrHash
240234
241235encodeDataHash32 ::
242236 DataHash ->
243- Maybe ( SizeHash HASH :~: 32 , DataHash32 )
237+ DataHash32
244238encodeDataHash32 dataHash = do
245- refl@ Refl <- sameNat (Proxy @ (SizeHash HASH )) (Proxy @ 32 )
246239 case hashToPackedBytes (extractHash dataHash) of
247- PackedBytes32 a b c d -> Just (refl, DataHash32 a b c d)
248- _ -> Nothing
240+ PackedBytes32 a b c d -> DataHash32 a b c d
241+ _ ->
242+ -- This case should never match, but if it does, we output garbage
243+ DataHash32 0xbb 0xbb 0xbb 0xbb
249244
250245getAdaOnly ::
251246 forall era .
@@ -269,15 +264,16 @@ pattern AlonzoTxOut addr vl dh <-
269264 where
270265 AlonzoTxOut (Addr network paymentCred stakeRef) vl SNothing
271266 | StakeRefBase stakeCred <- stakeRef
272- , Just adaCompact <- getAdaOnly (Proxy @ era ) vl
273- , Just ( Refl , addr28Extra) <- encodeAddress28 network paymentCred =
274- TxOut_AddrHash28_AdaOnly stakeCred addr28Extra adaCompact
267+ , Just adaCompact <- getAdaOnly (Proxy @ era ) vl =
268+ let addr28Extra = encodeAddress28 network paymentCred
269+ in TxOut_AddrHash28_AdaOnly stakeCred addr28Extra adaCompact
275270 AlonzoTxOut (Addr network paymentCred stakeRef) vl (SJust dh)
276271 | StakeRefBase stakeCred <- stakeRef
277- , Just adaCompact <- getAdaOnly (Proxy @ era ) vl
278- , Just (Refl , addr28Extra) <- encodeAddress28 network paymentCred
279- , Just (Refl , dataHash32) <- encodeDataHash32 dh =
280- TxOut_AddrHash28_AdaOnly_DataHash32 stakeCred addr28Extra adaCompact dataHash32
272+ , Just adaCompact <- getAdaOnly (Proxy @ era ) vl =
273+ let
274+ addr28Extra = encodeAddress28 network paymentCred
275+ dataHash32 = encodeDataHash32 dh
276+ in TxOut_AddrHash28_AdaOnly_DataHash32 stakeCred addr28Extra adaCompact dataHash32
281277 AlonzoTxOut addr vl mdh =
282278 let v = fromMaybe (error $ " Illegal value in TxOut: " ++ show vl) $ toCompact vl
283279 a = compactAddr addr
@@ -440,15 +436,12 @@ mkTxOutCompact addr cAddr cVal mdh
440436
441437getAlonzoTxOutDataHash ::
442438 forall era .
443- HasCallStack =>
444439 AlonzoTxOut era ->
445440 StrictMaybe DataHash
446441getAlonzoTxOutDataHash = \ case
447442 TxOutCompactDH' _ _ dh -> SJust dh
448443 TxOut_AddrHash28_AdaOnly_DataHash32 _ _ _ dh ->
449- case decodeDataHash32 dh of
450- Nothing -> error $ " Impossible: Compacted a DataHash of non-standard size: " ++ show dh
451- Just dataHash -> SJust dataHash
444+ SJust $! decodeDataHash32 dh
452445 _ -> SNothing
453446
454447getAlonzoTxOutEitherAddr ::
@@ -457,12 +450,10 @@ getAlonzoTxOutEitherAddr ::
457450getAlonzoTxOutEitherAddr = \ case
458451 TxOutCompact' cAddr _ -> Right cAddr
459452 TxOutCompactDH' cAddr _ _ -> Right cAddr
460- TxOut_AddrHash28_AdaOnly stakeRef addr28Extra _
461- | Just addr <- decodeAddress28 stakeRef addr28Extra -> Left addr
462- | otherwise -> error addressErrorMsg
463- TxOut_AddrHash28_AdaOnly_DataHash32 stakeRef addr28Extra _ _
464- | Just addr <- decodeAddress28 stakeRef addr28Extra -> Left addr
465- | otherwise -> error addressErrorMsg
453+ TxOut_AddrHash28_AdaOnly stakeRef addr28Extra _ ->
454+ Left $! decodeAddress28 stakeRef addr28Extra
455+ TxOut_AddrHash28_AdaOnly_DataHash32 stakeRef addr28Extra _ _ ->
456+ Left $! decodeAddress28 stakeRef addr28Extra
466457
467458-- | Compute an estimate of the size of storing one UTxO entry.
468459-- This function implements the UTxO entry size estimate done by scaledMinDeposit in the ShelleyMA era
0 commit comments