Types.hs (6093B)
1 {-# OPTIONS_HADDOCK hide #-} 2 {-# LANGUAGE DeriveGeneric #-} 3 4 -- | 5 -- Module: Lightning.Protocol.BOLT2.Types 6 -- Copyright: (c) 2025 Jared Tobin 7 -- License: MIT 8 -- Maintainer: Jared Tobin <jared@ppad.tech> 9 -- 10 -- Field types specific to BOLT #2. 11 12 module Lightning.Protocol.BOLT2.Types ( 13 HtlcId(..) 14 , SerialId(..) 15 , ScriptPubKey 16 , script_pubkey 17 , un_script_pubkey 18 , Witness 19 , witness 20 , un_witness 21 , OnionRoutingPacket 22 , onion_routing_packet 23 , un_onion_routing_packet 24 , OnionHash 25 , onion_hash 26 , un_onion_hash 27 , AttributionData 28 , attribution_data 29 , un_attribution_data 30 , FeeRange(..) 31 , NextFunding(..) 32 ) where 33 34 import Bitcoin.Prim.Tx (TxId) 35 import Control.DeepSeq (NFData) 36 import qualified Data.ByteString as BS 37 import Data.Word (Word8, Word64) 38 import GHC.Generics (Generic) 39 import Lightning.Protocol.BOLT1 (Satoshi) 40 41 -- | An HTLC identifier (the @id@ field of the HTLC messages). The 42 -- offerer numbers its HTLCs from 0, incrementing by 1. 43 newtype HtlcId = HtlcId Word64 44 deriving (Eq, Ord, Show, Generic) 45 46 instance NFData HtlcId 47 48 -- | The @serial_id@ of an input or output in interactive transaction 49 -- construction. The initiator sends even values, the non-initiator 50 -- odd ones. 51 newtype SerialId = SerialId Word64 52 deriving (Eq, Ord, Show, Generic) 53 54 instance NFData SerialId 55 56 -- | A scriptPubKey, at most 65535 bytes (the most a u16 length prefix 57 -- can describe). 58 newtype ScriptPubKey = ScriptPubKey BS.ByteString 59 deriving (Eq, Ord, Show, Generic) 60 61 instance NFData ScriptPubKey 62 63 -- | Construct a t'ScriptPubKey', failing above 65535 bytes. The script 64 -- itself isn't checked; the forms acceptable in @shutdown@ depend on 65 -- negotiated features. 66 -- 67 -- >>> script_pubkey "\x51\x02\x4e\x73" 68 -- Just (ScriptPubKey "Q\STXNs") 69 -- >>> script_pubkey (BS.replicate 65536 0x00) 70 -- Nothing 71 script_pubkey :: BS.ByteString -> Maybe ScriptPubKey 72 script_pubkey bs 73 | BS.length bs <= 65535 = Just (ScriptPubKey bs) 74 | otherwise = Nothing 75 {-# INLINE script_pubkey #-} 76 77 -- | The bytes of a t'ScriptPubKey'. 78 un_script_pubkey :: ScriptPubKey -> BS.ByteString 79 un_script_pubkey (ScriptPubKey bs) = bs 80 {-# INLINE un_script_pubkey #-} 81 82 -- | The serialized witness of one input in @tx_signatures@ (encoded as 83 -- in Bitcoin's wire protocol), at most 65535 bytes. 84 newtype Witness = Witness BS.ByteString 85 deriving (Eq, Ord, Show, Generic) 86 87 instance NFData Witness 88 89 -- | Construct a t'Witness', failing above 65535 bytes. The contents 90 -- aren't checked. 91 -- 92 -- >>> witness "\x01\x01\x2a" 93 -- Just (Witness "\SOH\SOH*") 94 witness :: BS.ByteString -> Maybe Witness 95 witness bs 96 | BS.length bs <= 65535 = Just (Witness bs) 97 | otherwise = Nothing 98 {-# INLINE witness #-} 99 100 -- | The bytes of a t'Witness'. 101 un_witness :: Witness -> BS.ByteString 102 un_witness (Witness bs) = bs 103 {-# INLINE un_witness #-} 104 105 -- | The 1366-byte @onion_routing_packet@ of @update_add_htlc@, kept 106 -- opaque (BOLT #4 defines its structure). 107 newtype OnionRoutingPacket = OnionRoutingPacket BS.ByteString 108 deriving (Eq, Ord, Show, Generic) 109 110 instance NFData OnionRoutingPacket 111 112 -- | Construct an t'OnionRoutingPacket' from exactly 1366 bytes. 113 -- 114 -- >>> let bs = BS.replicate 1366 0x00 115 -- >>> fmap un_onion_routing_packet (onion_routing_packet bs) == Just bs 116 -- True 117 -- >>> onion_routing_packet (BS.take 1365 bs) 118 -- Nothing 119 onion_routing_packet :: BS.ByteString -> Maybe OnionRoutingPacket 120 onion_routing_packet bs 121 | BS.length bs == 1366 = Just (OnionRoutingPacket bs) 122 | otherwise = Nothing 123 {-# INLINE onion_routing_packet #-} 124 125 -- | The bytes of an t'OnionRoutingPacket'. 126 un_onion_routing_packet :: OnionRoutingPacket -> BS.ByteString 127 un_onion_routing_packet (OnionRoutingPacket bs) = bs 128 {-# INLINE un_onion_routing_packet #-} 129 130 -- | The SHA256 hash of an onion routing packet (the @sha256_of_onion@ 131 -- field of @update_fail_malformed_htlc@). 132 newtype OnionHash = OnionHash BS.ByteString 133 deriving (Eq, Ord, Show, Generic) 134 135 instance NFData OnionHash 136 137 -- | Construct an t'OnionHash' from exactly 32 bytes. 138 -- 139 -- >>> onion_hash (BS.replicate 31 0x00) 140 -- Nothing 141 onion_hash :: BS.ByteString -> Maybe OnionHash 142 onion_hash bs 143 | BS.length bs == 32 = Just (OnionHash bs) 144 | otherwise = Nothing 145 {-# INLINE onion_hash #-} 146 147 -- | The bytes of an t'OnionHash'. 148 un_onion_hash :: OnionHash -> BS.ByteString 149 un_onion_hash (OnionHash bs) = bs 150 {-# INLINE un_onion_hash #-} 151 152 -- | The 920-byte @attribution_data@ of @update_fulfill_htlc@ and 153 -- @update_fail_htlc@: twenty u32 HTLC hold times followed by 210 154 -- four-byte truncated HMACs. Kept opaque (BOLT #4 defines its use). 155 newtype AttributionData = AttributionData BS.ByteString 156 deriving (Eq, Ord, Show, Generic) 157 158 instance NFData AttributionData 159 160 -- | Construct an t'AttributionData' from exactly 920 bytes. 161 -- 162 -- >>> let bs = BS.replicate 920 0x00 163 -- >>> fmap un_attribution_data (attribution_data bs) == Just bs 164 -- True 165 -- >>> attribution_data (BS.drop 1 bs) 166 -- Nothing 167 attribution_data :: BS.ByteString -> Maybe AttributionData 168 attribution_data bs 169 | BS.length bs == 920 = Just (AttributionData bs) 170 | otherwise = Nothing 171 {-# INLINE attribution_data #-} 172 173 -- | The bytes of an t'AttributionData'. 174 un_attribution_data :: AttributionData -> BS.ByteString 175 un_attribution_data (AttributionData bs) = bs 176 {-# INLINE un_attribution_data #-} 177 178 -- | The @fee_range@ of @closing_signed@: the fees the sender is 179 -- prepared to pay for the closing transaction. 180 data FeeRange = FeeRange 181 { fee_range_min_fee_satoshis :: {-# UNPACK #-} !Satoshi 182 , fee_range_max_fee_satoshis :: {-# UNPACK #-} !Satoshi 183 } deriving (Eq, Show, Generic) 184 185 instance NFData FeeRange 186 187 -- | The @next_funding@ record of @channel_reestablish@: an interactive 188 -- funding transaction whose signatures are still being exchanged. 189 data NextFunding = NextFunding 190 { next_funding_txid :: !TxId 191 , next_funding_retransmit_flags :: {-# UNPACK #-} !Word8 192 -- ^ bit 0: the sender wants @commitment_signed@ retransmitted 193 } deriving (Eq, Show, Generic) 194 195 instance NFData NextFunding