ppad-bolt1-0.0.1: bench/Weight.hs
{-# LANGUAGE BangPatterns #-}
{-# LANGUAGE OverloadedStrings #-}
module Main where
import qualified Data.ByteString as BS
import Data.Word (Word16, Word32, Word64)
import Data.Int (Int8, Int16, Int32, Int64)
import Lightning.Protocol.BOLT1
import Lightning.Protocol.BOLT1.Codec
import Lightning.Protocol.BOLT1.TLV (encodeTlvRecord)
import Weigh
-- Fixtures --------------------------------------------------------------------
-- Prevent constant folding with NOINLINE
{-# NOINLINE w16Val #-}
w16Val :: Word16
w16Val = 0x1234
{-# NOINLINE w32Val #-}
w32Val :: Word32
w32Val = 0x12345678
{-# NOINLINE w64Val #-}
w64Val :: Word64
w64Val = 0x0102030405060708
{-# NOINLINE s8Val #-}
s8Val :: Int8
s8Val = -42
{-# NOINLINE s16Val #-}
s16Val :: Int16
s16Val = -1000
{-# NOINLINE s32Val #-}
s32Val :: Int32
s32Val = -100000
{-# NOINLINE s64Val #-}
s64Val :: Int64
s64Val = -10000000000
{-# NOINLINE tu16Small #-}
tu16Small :: Word16
tu16Small = 0x7f
{-# NOINLINE tu16Full #-}
tu16Full :: Word16
tu16Full = 0xffff
{-# NOINLINE tu32Small #-}
tu32Small :: Word32
tu32Small = 0x42
{-# NOINLINE tu32Full #-}
tu32Full :: Word32
tu32Full = 0xffffffff
{-# NOINLINE tu64Small #-}
tu64Small :: Word64
tu64Small = 0x10
{-# NOINLINE tu64Full #-}
tu64Full :: Word64
tu64Full = 0xffffffffffffffff
{-# NOINLINE bigSizeSmall #-}
bigSizeSmall :: Word64
bigSizeSmall = 0xfc
{-# NOINLINE bigSizeMedium #-}
bigSizeMedium :: Word64
bigSizeMedium = 0x1000
{-# NOINLINE bigSizeLarge #-}
bigSizeLarge :: Word64
bigSizeLarge = 0x100000000
-- Pre-encoded bytes for decoder benchmarks
{-# NOINLINE u16Bytes #-}
u16Bytes :: BS.ByteString
u16Bytes = encodeU16 w16Val
{-# NOINLINE u32Bytes #-}
u32Bytes :: BS.ByteString
u32Bytes = encodeU32 w32Val
{-# NOINLINE u64Bytes #-}
u64Bytes :: BS.ByteString
u64Bytes = encodeU64 w64Val
{-# NOINLINE s8Bytes #-}
s8Bytes :: BS.ByteString
s8Bytes = encodeS8 s8Val
{-# NOINLINE s16Bytes #-}
s16Bytes :: BS.ByteString
s16Bytes = encodeS16 s16Val
{-# NOINLINE s32Bytes #-}
s32Bytes :: BS.ByteString
s32Bytes = encodeS32 s32Val
{-# NOINLINE s64Bytes #-}
s64Bytes :: BS.ByteString
s64Bytes = encodeS64 s64Val
{-# NOINLINE bigSizeBytes #-}
bigSizeBytes :: BS.ByteString
bigSizeBytes = encodeBigSize bigSizeLarge
-- TLV fixtures
{-# NOINLINE tlvRecord1 #-}
tlvRecord1 :: TlvRecord
tlvRecord1 = TlvRecord 1 "test-value"
{-# NOINLINE tlvStream1 #-}
tlvStream1 :: TlvStream
tlvStream1 = unsafeTlvStream [tlvRecord1]
{-# NOINLINE tlvStream5 #-}
tlvStream5 :: TlvStream
tlvStream5 = unsafeTlvStream
[ TlvRecord 1 "value1"
, TlvRecord 3 "value3"
, TlvRecord 5 "value5"
, TlvRecord 7 "value7"
, TlvRecord 9 "value9"
]
{-# NOINLINE tlvStream20 #-}
tlvStream20 :: TlvStream
tlvStream20 = unsafeTlvStream
[ TlvRecord (2 * i + 1) (BS.replicate 10 (fromIntegral i))
| i <- [0..19]
]
{-# NOINLINE tlvStreamBytes1 #-}
tlvStreamBytes1 :: BS.ByteString
tlvStreamBytes1 = encodeTlvStream tlvStream1
{-# NOINLINE tlvStreamBytes5 #-}
tlvStreamBytes5 :: BS.ByteString
tlvStreamBytes5 = encodeTlvStream tlvStream5
{-# NOINLINE tlvStreamBytes20 #-}
tlvStreamBytes20 :: BS.ByteString
tlvStreamBytes20 = encodeTlvStream tlvStream20
-- Message fixtures
{-# NOINLINE minimalInit #-}
minimalInit :: Init
minimalInit = Init BS.empty BS.empty []
{-# NOINLINE initWithFeatures #-}
initWithFeatures :: Init
initWithFeatures = Init "\x00\x08" "\x00\x0a\x8a" []
{-# NOINLINE initWithTlvs #-}
initWithTlvs :: Init
initWithTlvs = Init BS.empty "\x00\x01" [InitRemoteAddr "127.0.0.1"]
{-# NOINLINE errorMsg #-}
errorMsg :: Error
errorMsg = Error allChannels "something bad happened"
{-# NOINLINE warningMsg #-}
warningMsg :: Warning
warningMsg = Warning allChannels "something concerning"
{-# NOINLINE pingMinimal #-}
pingMinimal :: Ping
pingMinimal = Ping 4 BS.empty
{-# NOINLINE pingWithPadding #-}
pingWithPadding :: Ping
pingWithPadding = Ping 4 (BS.replicate 64 0x00)
{-# NOINLINE pongMsg #-}
pongMsg :: Pong
pongMsg = Pong (BS.replicate 4 0x00)
{-# NOINLINE peerStorageMsg #-}
peerStorageMsg :: PeerStorage
peerStorageMsg = PeerStorage (BS.replicate 100 0xab)
{-# NOINLINE peerStorageRetrievalMsg #-}
peerStorageRetrievalMsg :: PeerStorageRetrieval
peerStorageRetrievalMsg = PeerStorageRetrieval (BS.replicate 50 0xcd)
-- Pre-encoded message bytes for decoder benchmarks
{-# NOINLINE initMinimalBytes #-}
initMinimalBytes :: BS.ByteString
initMinimalBytes = either (const BS.empty) id (encodeInit minimalInit)
{-# NOINLINE initWithTlvsBytes #-}
initWithTlvsBytes :: BS.ByteString
initWithTlvsBytes = either (const BS.empty) id (encodeInit initWithTlvs)
{-# NOINLINE errorBytes #-}
errorBytes :: BS.ByteString
errorBytes = either (const BS.empty) id (encodeError errorMsg)
{-# NOINLINE warningBytes #-}
warningBytes :: BS.ByteString
warningBytes = either (const BS.empty) id (encodeWarning warningMsg)
{-# NOINLINE pingMinimalBytes #-}
pingMinimalBytes :: BS.ByteString
pingMinimalBytes = either (const BS.empty) id (encodePing pingMinimal)
{-# NOINLINE pingWithPaddingBytes #-}
pingWithPaddingBytes :: BS.ByteString
pingWithPaddingBytes = either (const BS.empty) id (encodePing pingWithPadding)
{-# NOINLINE pongBytes #-}
pongBytes :: BS.ByteString
pongBytes = either (const BS.empty) id (encodePong pongMsg)
{-# NOINLINE peerStorageBytes #-}
peerStorageBytes :: BS.ByteString
peerStorageBytes = either (const BS.empty) id (encodePeerStorage peerStorageMsg)
{-# NOINLINE peerStorageRetrievalBytes #-}
peerStorageRetrievalBytes :: BS.ByteString
peerStorageRetrievalBytes =
either (const BS.empty) id (encodePeerStorageRetrieval peerStorageRetrievalMsg)
-- Envelope fixtures
{-# NOINLINE initMessage #-}
initMessage :: Message
initMessage = MsgInitVal minimalInit
{-# NOINLINE pingMessage #-}
pingMessage :: Message
pingMessage = MsgPingVal pingMinimal
{-# NOINLINE envelopeBytes #-}
envelopeBytes :: BS.ByteString
envelopeBytes = either (const BS.empty) id (encodeEnvelope initMessage Nothing)
-- Main ------------------------------------------------------------------------
main :: IO ()
main = mainWith $ do
setColumns [Case, Allocated, GCs, Max]
-- Primitive encoders --------------------------------------------------------
wgroup "Primitive Encoders" $ do
func "encodeU16" encodeU16 w16Val
func "encodeU32" encodeU32 w32Val
func "encodeU64" encodeU64 w64Val
func "encodeS8" encodeS8 s8Val
func "encodeS16" encodeS16 s16Val
func "encodeS32" encodeS32 s32Val
func "encodeS64" encodeS64 s64Val
wgroup "Truncated Unsigned Encoders" $ do
func "encodeTu16/small" encodeTu16 tu16Small
func "encodeTu16/full" encodeTu16 tu16Full
func "encodeTu32/small" encodeTu32 tu32Small
func "encodeTu32/full" encodeTu32 tu32Full
func "encodeTu64/small" encodeTu64 tu64Small
func "encodeTu64/full" encodeTu64 tu64Full
wgroup "Minimal Signed Encoder" $ do
func "encodeMinSigned/1-byte" encodeMinSigned (0 :: Int64)
func "encodeMinSigned/2-byte" encodeMinSigned (1000 :: Int64)
func "encodeMinSigned/4-byte" encodeMinSigned (100000 :: Int64)
func "encodeMinSigned/8-byte" encodeMinSigned s64Val
wgroup "BigSize Encoder" $ do
func "encodeBigSize/1-byte" encodeBigSize bigSizeSmall
func "encodeBigSize/3-byte" encodeBigSize bigSizeMedium
func "encodeBigSize/9-byte" encodeBigSize bigSizeLarge
-- Primitive decoders --------------------------------------------------------
wgroup "Primitive Decoders" $ do
func "decodeU16" decodeU16 u16Bytes
func "decodeU32" decodeU32 u32Bytes
func "decodeU64" decodeU64 u64Bytes
func "decodeS8" decodeS8 s8Bytes
func "decodeS16" decodeS16 s16Bytes
func "decodeS32" decodeS32 s32Bytes
func "decodeS64" decodeS64 s64Bytes
func "decodeBigSize" decodeBigSize bigSizeBytes
-- TLV operations ------------------------------------------------------------
wgroup "TLV Encoding" $ do
func "encodeTlvRecord" encodeTlvRecord tlvRecord1
func "encodeTlvStream/1-record" encodeTlvStream tlvStream1
func "encodeTlvStream/5-records" encodeTlvStream tlvStream5
func "encodeTlvStream/20-records" encodeTlvStream tlvStream20
wgroup "TLV Decoding" $ do
func "decodeTlvStreamRaw/1-record" decodeTlvStreamRaw tlvStreamBytes1
func "decodeTlvStreamRaw/5-records" decodeTlvStreamRaw tlvStreamBytes5
func "decodeTlvStreamRaw/20-records" decodeTlvStreamRaw tlvStreamBytes20
func "decodeTlvStream/1-record" decodeTlvStream tlvStreamBytes1
func "decodeTlvStream/5-records" decodeTlvStream tlvStreamBytes5
-- Message encoders ----------------------------------------------------------
wgroup "Message Encoders" $ do
func "encodeInit/minimal" encodeInit minimalInit
func "encodeInit/with-features" encodeInit initWithFeatures
func "encodeInit/with-tlvs" encodeInit initWithTlvs
func "encodeError" encodeError errorMsg
func "encodeWarning" encodeWarning warningMsg
func "encodePing/minimal" encodePing pingMinimal
func "encodePing/with-padding" encodePing pingWithPadding
func "encodePong" encodePong pongMsg
func "encodePeerStorage" encodePeerStorage peerStorageMsg
func "encodePeerStorageRetrieval" encodePeerStorageRetrieval
peerStorageRetrievalMsg
-- Message decoders ----------------------------------------------------------
wgroup "Message Decoders" $ do
func "decodeInit/minimal" decodeInit initMinimalBytes
func "decodeInit/with-tlvs" decodeInit initWithTlvsBytes
func "decodeError" decodeError errorBytes
func "decodeWarning" decodeWarning warningBytes
func "decodePing/minimal" decodePing pingMinimalBytes
func "decodePing/with-padding" decodePing pingWithPaddingBytes
func "decodePong" decodePong pongBytes
func "decodePeerStorage" decodePeerStorage peerStorageBytes
func "decodePeerStorageRetrieval" decodePeerStorageRetrieval
peerStorageRetrievalBytes
-- Envelope operations -------------------------------------------------------
wgroup "Envelope Operations" $ do
func "encodeEnvelope/init" (flip encodeEnvelope Nothing) initMessage
func "encodeEnvelope/ping" (flip encodeEnvelope Nothing) pingMessage
func "decodeEnvelope" decodeEnvelope envelopeBytes