{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE DerivingStrategies #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE ViewPatterns #-}
module Crypto.Curve.Secp256k1 (
Context(..)
, wcontext
, wrcontext
, Sig
, sign_ecdsa
, verify_ecdsa
, sign_schnorr
, verify_schnorr
, ecdh
, parse_der
, serialize_der
, parse_compact
, serialize_compact
, Pub(..)
, derive_pub
, parse_pub
, tweak_pub_add
, tweak_pub_mul
, tweak_sec_add
, tweak_sec_mul
, serialize_pub
, serialize_pub_u
, XOnlyPub(..)
, xonly
, parse_xonly
, serialize_xonly
, KeyPair
, keypair
, keypair_pub
, keypair_sec
, Secp256k1Exception(..)
) where
import Control.Exception (Exception, bracket, throwIO)
import Control.Monad (when)
import Crypto.Curve.Secp256k1.Internal hiding (Context, wcontext)
import qualified Crypto.Curve.Secp256k1.Internal as I (Context)
import GHC.Generics
import qualified Data.ByteString as BS
import qualified Foreign.Marshal.Alloc as A (alloca, allocaBytes)
import Foreign.Ptr (Ptr)
import qualified Foreign.Ptr as F (castPtr, nullPtr)
import qualified Foreign.Storable as S (poke, peek)
newtype Context = Context (Ptr I.Context)
deriving stock (forall x. Context -> Rep Context x)
-> (forall x. Rep Context x -> Context) -> Generic Context
forall x. Rep Context x -> Context
forall x. Context -> Rep Context x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. Context -> Rep Context x
from :: forall x. Context -> Rep Context x
$cto :: forall x. Rep Context x -> Context
to :: forall x. Rep Context x -> Context
Generic
instance Show Context where
show :: Context -> String
show (Context Ptr Context
tex) = String
"<bitcoin-core/secp256k1 context " String -> ShowS
forall a. Semigroup a => a -> a -> a
<> Ptr Context -> String
forall a. Show a => a -> String
show Ptr Context
tex String -> ShowS
forall a. Semigroup a => a -> a -> a
<> String
">"
newtype Pub = Pub BS.ByteString
deriving stock (forall x. Pub -> Rep Pub x)
-> (forall x. Rep Pub x -> Pub) -> Generic Pub
forall x. Rep Pub x -> Pub
forall x. Pub -> Rep Pub x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. Pub -> Rep Pub x
from :: forall x. Pub -> Rep Pub x
$cto :: forall x. Rep Pub x -> Pub
to :: forall x. Rep Pub x -> Pub
Generic
instance Show Pub where
show :: Pub -> String
show Pub
_ = String
"<bitcoin-core/secp256k1 public key>"
newtype XOnlyPub = XOnlyPub BS.ByteString
deriving stock (forall x. XOnlyPub -> Rep XOnlyPub x)
-> (forall x. Rep XOnlyPub x -> XOnlyPub) -> Generic XOnlyPub
forall x. Rep XOnlyPub x -> XOnlyPub
forall x. XOnlyPub -> Rep XOnlyPub x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. XOnlyPub -> Rep XOnlyPub x
from :: forall x. XOnlyPub -> Rep XOnlyPub x
$cto :: forall x. Rep XOnlyPub x -> XOnlyPub
to :: forall x. Rep XOnlyPub x -> XOnlyPub
Generic
instance Show XOnlyPub where
show :: XOnlyPub -> String
show XOnlyPub
_ = String
"<bitcoin-core/secp256k1 x-only public key>"
newtype KeyPair = KeyPair BS.ByteString
deriving stock (forall x. KeyPair -> Rep KeyPair x)
-> (forall x. Rep KeyPair x -> KeyPair) -> Generic KeyPair
forall x. Rep KeyPair x -> KeyPair
forall x. KeyPair -> Rep KeyPair x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. KeyPair -> Rep KeyPair x
from :: forall x. KeyPair -> Rep KeyPair x
$cto :: forall x. Rep KeyPair x -> KeyPair
to :: forall x. Rep KeyPair x -> KeyPair
Generic
instance Show KeyPair where
show :: KeyPair -> String
show KeyPair
_ = String
"<bitcoin-core/secp256k1 keypair>"
newtype Sig = Sig BS.ByteString
deriving stock (forall x. Sig -> Rep Sig x)
-> (forall x. Rep Sig x -> Sig) -> Generic Sig
forall x. Rep Sig x -> Sig
forall x. Sig -> Rep Sig x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. Sig -> Rep Sig x
from :: forall x. Sig -> Rep Sig x
$cto :: forall x. Rep Sig x -> Sig
to :: forall x. Rep Sig x -> Sig
Generic
instance Show Sig where
show :: Sig -> String
show Sig
_ = String
"<bitcoin-core/secp256k1 signature>"
data Secp256k1Exception =
Secp256k1Error
| CSecp256k1Error
deriving Int -> Secp256k1Exception -> ShowS
[Secp256k1Exception] -> ShowS
Secp256k1Exception -> String
(Int -> Secp256k1Exception -> ShowS)
-> (Secp256k1Exception -> String)
-> ([Secp256k1Exception] -> ShowS)
-> Show Secp256k1Exception
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> Secp256k1Exception -> ShowS
showsPrec :: Int -> Secp256k1Exception -> ShowS
$cshow :: Secp256k1Exception -> String
show :: Secp256k1Exception -> String
$cshowList :: [Secp256k1Exception] -> ShowS
showList :: [Secp256k1Exception] -> ShowS
Show
instance Exception Secp256k1Exception
wcontext
:: (Context -> IO ())
-> IO ()
wcontext :: (Context -> IO ()) -> IO ()
wcontext = IO Context -> (Context -> IO ()) -> (Context -> IO ()) -> IO ()
forall a b c. IO a -> (a -> IO b) -> (a -> IO c) -> IO c
bracket IO Context
create Context -> IO ()
destroy where
create :: IO Context
create = do
Ptr Context
tex <- CUInt -> IO (Ptr Context)
secp256k1_context_create CUInt
forall a. Integral a => a
_SECP256K1_CONTEXT_NONE
Context -> IO Context
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Ptr Context -> Context
Context Ptr Context
tex)
destroy :: Context -> IO ()
destroy (Context Ptr Context
tex) =
Ptr Context -> IO ()
secp256k1_context_destroy Ptr Context
tex
wrcontext
:: BS.ByteString
-> (Context -> IO ())
-> IO ()
wrcontext :: ByteString -> (Context -> IO ()) -> IO ()
wrcontext ByteString
enn Context -> IO ()
con
| ByteString -> Int
BS.length ByteString
enn Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = IO Context -> (Context -> IO ()) -> (Context -> IO ()) -> IO ()
forall a b c. IO a -> (a -> IO b) -> (a -> IO c) -> IO c
bracket IO Context
create Context -> IO ()
destroy Context -> IO ()
con
where
create :: IO Context
create = do
Ptr Context
tex <- CUInt -> IO (Ptr Context)
secp256k1_context_create CUInt
forall a. Integral a => a
_SECP256K1_CONTEXT_NONE
ByteString -> (CString -> IO Context) -> IO Context
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
enn ((CString -> IO Context) -> IO Context)
-> (CString -> IO Context) -> IO Context
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Seed32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Seed32
sed) -> do
CInt
suc <- Ptr Context -> Ptr Seed32 -> IO CInt
secp256k1_context_randomize Ptr Context
tex Ptr Seed32
sed
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
Context -> IO Context
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Ptr Context -> Context
Context Ptr Context
tex)
destroy :: Context -> IO ()
destroy (Context Ptr Context
tex) =
Ptr Context -> IO ()
secp256k1_context_destroy Ptr Context
tex
derive_pub
:: Context
-> BS.ByteString
-> IO Pub
derive_pub :: Context -> ByteString -> IO Pub
derive_pub (Context Ptr Context
tex) ByteString
bs
| ByteString -> Int
BS.length ByteString
bs Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO Pub
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = ByteString -> (CString -> IO Pub) -> IO Pub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
bs ((CString -> IO Pub) -> IO Pub) -> (CString -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr SecKey32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr SecKey32
sec) ->
Int -> (Ptr PubKey64 -> IO Pub) -> IO Pub
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_PUB_BYTES_INTERNAL ((Ptr PubKey64 -> IO Pub) -> IO Pub)
-> (Ptr PubKey64 -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \Ptr PubKey64
out -> do
CInt
suc <- Ptr Context -> Ptr PubKey64 -> Ptr SecKey32 -> IO CInt
secp256k1_ec_pubkey_create Ptr Context
tex Ptr PubKey64
out Ptr SecKey32
sec
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let pub :: Ptr b
pub = Ptr PubKey64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr PubKey64
out
ByteString
key <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
pub, Int
_PUB_BYTES_INTERNAL)
Pub -> IO Pub
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Pub
Pub ByteString
key)
parse_pub
:: Context
-> BS.ByteString
-> IO Pub
parse_pub :: Context -> ByteString -> IO Pub
parse_pub (Context Ptr Context
tex) ByteString
bs =
ByteString -> (CStringLen -> IO Pub) -> IO Pub
forall a. ByteString -> (CStringLen -> IO a) -> IO a
BS.useAsCStringLen ByteString
bs ((CStringLen -> IO Pub) -> IO Pub)
-> (CStringLen -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr CUChar
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr CUChar
pub, Int -> CSize
forall a b. (Integral a, Num b) => a -> b
fromIntegral -> CSize
len) ->
Int -> (Ptr PubKey64 -> IO Pub) -> IO Pub
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_PUB_BYTES_INTERNAL ((Ptr PubKey64 -> IO Pub) -> IO Pub)
-> (Ptr PubKey64 -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \Ptr PubKey64
out -> do
CInt
suc <- Ptr Context -> Ptr PubKey64 -> Ptr CUChar -> CSize -> IO CInt
secp256k1_ec_pubkey_parse Ptr Context
tex Ptr PubKey64
out Ptr CUChar
pub CSize
len
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let par :: Ptr b
par = Ptr PubKey64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr PubKey64
out
ByteString
key <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
par, Int
_PUB_BYTES_INTERNAL)
Pub -> IO Pub
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Pub
Pub ByteString
key)
data PubFormat =
Compressed
| Uncompressed
serialize_pub
:: Context
-> Pub
-> IO BS.ByteString
serialize_pub :: Context -> Pub -> IO ByteString
serialize_pub = PubFormat -> Context -> Pub -> IO ByteString
serialize_pub_in PubFormat
Compressed
serialize_pub_u
:: Context
-> Pub
-> IO BS.ByteString
serialize_pub_u :: Context -> Pub -> IO ByteString
serialize_pub_u = PubFormat -> Context -> Pub -> IO ByteString
serialize_pub_in PubFormat
Uncompressed
serialize_pub_in :: PubFormat -> Context -> Pub -> IO BS.ByteString
serialize_pub_in :: PubFormat -> Context -> Pub -> IO ByteString
serialize_pub_in PubFormat
for (Context Ptr Context
tex) (Pub ByteString
pub) =
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
pub ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr PubKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr PubKey64
key) ->
(Ptr CSize -> IO ByteString) -> IO ByteString
forall a b. Storable a => (Ptr a -> IO b) -> IO b
A.alloca ((Ptr CSize -> IO ByteString) -> IO ByteString)
-> (Ptr CSize -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr CSize
len ->
Int -> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
bys ((Ptr CUChar -> IO ByteString) -> IO ByteString)
-> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr CUChar
out -> do
let siz :: CSize
siz = Int -> CSize
forall a b. (Integral a, Num b) => a -> b
fromIntegral Int
bys
Ptr CSize -> CSize -> IO ()
forall a. Storable a => Ptr a -> a -> IO ()
S.poke Ptr CSize
len CSize
siz
CInt
suc <- Ptr Context
-> Ptr CUChar -> Ptr CSize -> Ptr PubKey64 -> CUInt -> IO CInt
secp256k1_ec_pubkey_serialize Ptr Context
tex Ptr CUChar
out Ptr CSize
len Ptr PubKey64
key CUInt
fal
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
CSize
pec <- Ptr CSize -> IO CSize
forall a. Storable a => Ptr a -> IO a
S.peek Ptr CSize
len
let enc :: Ptr b
enc = Ptr CUChar -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr CUChar
out
nel :: Int
nel = CSize -> Int
forall a b. (Integral a, Num b) => a -> b
fromIntegral CSize
pec
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
nel)
where
bys :: Int
bys = case PubFormat
for of
PubFormat
Compressed -> Int
_PUB_BYTES_COMPRESSED
PubFormat
Uncompressed -> Int
_PUB_BYTES_UNCOMPRESSED
fal :: CUInt
fal = case PubFormat
for of
PubFormat
Compressed -> CUInt
_COMPRESSED_FLAG
PubFormat
Uncompressed -> CUInt
_UNCOMPRESSED_FLAG
tweak_pub_add
:: Context
-> Pub
-> BS.ByteString
-> IO Pub
tweak_pub_add :: Context -> Pub -> ByteString -> IO Pub
tweak_pub_add (Context Ptr Context
tex) (Pub ByteString
pub) ByteString
wee
| ByteString -> Int
BS.length ByteString
wee Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO Pub
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = do
let cop :: ByteString
cop = ByteString -> ByteString
BS.copy ByteString
pub
ByteString -> (CString -> IO Pub) -> IO Pub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
cop ((CString -> IO Pub) -> IO Pub) -> (CString -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr PubKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr PubKey64
out) ->
ByteString -> (CString -> IO Pub) -> IO Pub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
wee ((CString -> IO Pub) -> IO Pub) -> (CString -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Tweak32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Tweak32
eek) -> do
CInt
suc <- Ptr Context -> Ptr PubKey64 -> Ptr Tweak32 -> IO CInt
secp256k1_ec_pubkey_tweak_add Ptr Context
tex Ptr PubKey64
out Ptr Tweak32
eek
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let enc :: Ptr b
enc = Ptr PubKey64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr PubKey64
out
ByteString
key <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_PUB_BYTES_INTERNAL)
Pub -> IO Pub
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Pub
Pub ByteString
key)
tweak_pub_mul
:: Context
-> Pub
-> BS.ByteString
-> IO Pub
tweak_pub_mul :: Context -> Pub -> ByteString -> IO Pub
tweak_pub_mul (Context Ptr Context
tex) (Pub ByteString
pub) ByteString
wee
| ByteString -> Int
BS.length ByteString
wee Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO Pub
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = do
let cop :: ByteString
cop = ByteString -> ByteString
BS.copy ByteString
pub
ByteString -> (CString -> IO Pub) -> IO Pub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
cop ((CString -> IO Pub) -> IO Pub) -> (CString -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr PubKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr PubKey64
out) ->
ByteString -> (CString -> IO Pub) -> IO Pub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
wee ((CString -> IO Pub) -> IO Pub) -> (CString -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Tweak32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Tweak32
eek) -> do
CInt
suc <- Ptr Context -> Ptr PubKey64 -> Ptr Tweak32 -> IO CInt
secp256k1_ec_pubkey_tweak_mul Ptr Context
tex Ptr PubKey64
out Ptr Tweak32
eek
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let enc :: Ptr b
enc = Ptr PubKey64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr PubKey64
out
ByteString
key <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_PUB_BYTES_INTERNAL)
Pub -> IO Pub
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Pub
Pub ByteString
key)
tweak_sec_add
:: Context
-> BS.ByteString
-> BS.ByteString
-> IO BS.ByteString
tweak_sec_add :: Context -> ByteString -> ByteString -> IO ByteString
tweak_sec_add (Context Ptr Context
tex) ByteString
key ByteString
wee
| ByteString -> Int
BS.length ByteString
key Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 Bool -> Bool -> Bool
|| ByteString -> Int
BS.length ByteString
wee Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO ByteString
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = do
let sec :: ByteString
sec = ByteString -> ByteString
BS.copy ByteString
key
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sec ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr SecKey32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr SecKey32
out) ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
wee ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Tweak32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Tweak32
eek) -> do
CInt
suc <- Ptr Context -> Ptr SecKey32 -> Ptr Tweak32 -> IO CInt
secp256k1_ec_seckey_tweak_add Ptr Context
tex Ptr SecKey32
out Ptr Tweak32
eek
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let enc :: Ptr b
enc = Ptr SecKey32 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr SecKey32
out
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_SEC_BYTES)
tweak_sec_mul
:: Context
-> BS.ByteString
-> BS.ByteString
-> IO BS.ByteString
tweak_sec_mul :: Context -> ByteString -> ByteString -> IO ByteString
tweak_sec_mul (Context Ptr Context
tex) ByteString
key ByteString
wee
| ByteString -> Int
BS.length ByteString
key Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 Bool -> Bool -> Bool
|| ByteString -> Int
BS.length ByteString
wee Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO ByteString
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = do
let sec :: ByteString
sec = ByteString -> ByteString
BS.copy ByteString
key
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sec ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr SecKey32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr SecKey32
out) ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
wee ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Tweak32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Tweak32
eek) -> do
CInt
suc <- Ptr Context -> Ptr SecKey32 -> Ptr Tweak32 -> IO CInt
secp256k1_ec_seckey_tweak_mul Ptr Context
tex Ptr SecKey32
out Ptr Tweak32
eek
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let enc :: Ptr b
enc = Ptr SecKey32 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr SecKey32
out
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_SEC_BYTES)
sign_ecdsa
:: Context
-> BS.ByteString
-> BS.ByteString
-> IO Sig
sign_ecdsa :: Context -> ByteString -> ByteString -> IO Sig
sign_ecdsa (Context Ptr Context
tex) ByteString
key ByteString
msg
| ByteString -> Int
BS.length ByteString
key Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 Bool -> Bool -> Bool
|| ByteString -> Int
BS.length ByteString
msg Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO Sig
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = Int -> (Ptr Sig64 -> IO Sig) -> IO Sig
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_SIG_BYTES ((Ptr Sig64 -> IO Sig) -> IO Sig)
-> (Ptr Sig64 -> IO Sig) -> IO Sig
forall a b. (a -> b) -> a -> b
$ \Ptr Sig64
out ->
ByteString -> (CString -> IO Sig) -> IO Sig
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
msg ((CString -> IO Sig) -> IO Sig) -> (CString -> IO Sig) -> IO Sig
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr MsgHash32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr MsgHash32
has) ->
ByteString -> (CString -> IO Sig) -> IO Sig
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
key ((CString -> IO Sig) -> IO Sig) -> (CString -> IO Sig) -> IO Sig
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr SecKey32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr SecKey32
sec) -> do
CInt
suc <- Ptr Context
-> Ptr Sig64
-> Ptr MsgHash32
-> Ptr SecKey32
-> Ptr Any
-> Ptr Any
-> IO CInt
forall a b.
Ptr Context
-> Ptr Sig64
-> Ptr MsgHash32
-> Ptr SecKey32
-> Ptr a
-> Ptr b
-> IO CInt
secp256k1_ecdsa_sign Ptr Context
tex Ptr Sig64
out Ptr MsgHash32
has Ptr SecKey32
sec Ptr Any
forall {b}. Ptr b
F.nullPtr Ptr Any
forall {b}. Ptr b
F.nullPtr
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let sig :: Ptr b
sig = Ptr Sig64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr Sig64
out
ByteString
enc <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
sig, Int
_SIG_BYTES)
Sig -> IO Sig
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Sig
Sig ByteString
enc)
verify_ecdsa
:: Context
-> Pub
-> BS.ByteString
-> Sig
-> IO Bool
verify_ecdsa :: Context -> Pub -> ByteString -> Sig -> IO Bool
verify_ecdsa (Context Ptr Context
tex) (Pub ByteString
pub) ByteString
msg (Sig ByteString
sig)
| ByteString -> Int
BS.length ByteString
msg Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO Bool
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = ByteString -> (CString -> IO Bool) -> IO Bool
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
pub ((CString -> IO Bool) -> IO Bool)
-> (CString -> IO Bool) -> IO Bool
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr PubKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr PubKey64
key) ->
ByteString -> (CString -> IO Bool) -> IO Bool
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sig ((CString -> IO Bool) -> IO Bool)
-> (CString -> IO Bool) -> IO Bool
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Sig64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Sig64
sip) ->
ByteString -> (CString -> IO Bool) -> IO Bool
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
msg ((CString -> IO Bool) -> IO Bool)
-> (CString -> IO Bool) -> IO Bool
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr MsgHash32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr MsgHash32
has) -> do
CInt
suc <- Ptr Context
-> Ptr Sig64 -> Ptr MsgHash32 -> Ptr PubKey64 -> IO CInt
secp256k1_ecdsa_verify Ptr Context
tex Ptr Sig64
sip Ptr MsgHash32
has Ptr PubKey64
key
Bool -> IO Bool
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
== CInt
1)
parse_der
:: Context
-> BS.ByteString
-> IO Sig
parse_der :: Context -> ByteString -> IO Sig
parse_der (Context Ptr Context
tex) ByteString
bs =
ByteString -> (CStringLen -> IO Sig) -> IO Sig
forall a. ByteString -> (CStringLen -> IO a) -> IO a
BS.useAsCStringLen ByteString
bs ((CStringLen -> IO Sig) -> IO Sig)
-> (CStringLen -> IO Sig) -> IO Sig
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr CUChar
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr CUChar
der, Int -> CSize
forall a b. (Integral a, Num b) => a -> b
fromIntegral -> CSize
len) ->
Int -> (Ptr Sig64 -> IO Sig) -> IO Sig
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_SIG_BYTES ((Ptr Sig64 -> IO Sig) -> IO Sig)
-> (Ptr Sig64 -> IO Sig) -> IO Sig
forall a b. (a -> b) -> a -> b
$ \Ptr Sig64
out -> do
CInt
suc <- Ptr Context -> Ptr Sig64 -> Ptr CUChar -> CSize -> IO CInt
secp256k1_ecdsa_signature_parse_der Ptr Context
tex Ptr Sig64
out Ptr CUChar
der CSize
len
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let par :: Ptr b
par = Ptr Sig64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr Sig64
out
ByteString
sig <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
par, Int
_SIG_BYTES)
Sig -> IO Sig
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Sig
Sig ByteString
sig)
serialize_der
:: Context
-> Sig
-> IO BS.ByteString
serialize_der :: Context -> Sig -> IO ByteString
serialize_der (Context Ptr Context
tex) (Sig ByteString
sig) =
(Ptr CSize -> IO ByteString) -> IO ByteString
forall a b. Storable a => (Ptr a -> IO b) -> IO b
A.alloca ((Ptr CSize -> IO ByteString) -> IO ByteString)
-> (Ptr CSize -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr CSize
len ->
Int -> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_DER_BYTES ((Ptr CUChar -> IO ByteString) -> IO ByteString)
-> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr CUChar
out ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sig ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Sig64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Sig64
sip) -> do
let siz :: CSize
siz = Int -> CSize
forall a b. (Integral a, Num b) => a -> b
fromIntegral Int
_DER_BYTES
Ptr CSize -> CSize -> IO ()
forall a. Storable a => Ptr a -> a -> IO ()
S.poke Ptr CSize
len CSize
siz
CInt
suc <- Ptr Context -> Ptr CUChar -> Ptr CSize -> Ptr Sig64 -> IO CInt
secp256k1_ecdsa_signature_serialize_der Ptr Context
tex Ptr CUChar
out Ptr CSize
len Ptr Sig64
sip
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
CSize
pek <- Ptr CSize -> IO CSize
forall a. Storable a => Ptr a -> IO a
S.peek Ptr CSize
len
let der :: Ptr b
der = Ptr CUChar -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr CUChar
out
nel :: Int
nel = CSize -> Int
forall a b. (Integral a, Num b) => a -> b
fromIntegral CSize
pek
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
der, Int
nel)
parse_compact
:: Context
-> BS.ByteString
-> IO Sig
parse_compact :: Context -> ByteString -> IO Sig
parse_compact (Context Ptr Context
tex) ByteString
bs =
ByteString -> (CString -> IO Sig) -> IO Sig
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
bs ((CString -> IO Sig) -> IO Sig) -> (CString -> IO Sig) -> IO Sig
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr CUChar
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr CUChar
com) ->
Int -> (Ptr Sig64 -> IO Sig) -> IO Sig
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_SIG_BYTES ((Ptr Sig64 -> IO Sig) -> IO Sig)
-> (Ptr Sig64 -> IO Sig) -> IO Sig
forall a b. (a -> b) -> a -> b
$ \Ptr Sig64
out -> do
CInt
suc <- Ptr Context -> Ptr Sig64 -> Ptr CUChar -> IO CInt
secp256k1_ecdsa_signature_parse_compact Ptr Context
tex Ptr Sig64
out Ptr CUChar
com
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let par :: Ptr b
par = Ptr Sig64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr Sig64
out
ByteString
enc <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
par, Int
_SIG_BYTES)
Sig -> IO Sig
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Sig
Sig ByteString
enc)
serialize_compact
:: Context
-> Sig
-> IO BS.ByteString
serialize_compact :: Context -> Sig -> IO ByteString
serialize_compact (Context Ptr Context
tex) (Sig ByteString
sig) =
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sig ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Sig64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Sig64
sip) ->
Int -> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_SIG_BYTES ((Ptr CUChar -> IO ByteString) -> IO ByteString)
-> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr CUChar
out -> do
CInt
_ <- Ptr Context -> Ptr CUChar -> Ptr Sig64 -> IO CInt
secp256k1_ecdsa_signature_serialize_compact Ptr Context
tex Ptr CUChar
out Ptr Sig64
sip
let enc :: Ptr b
enc = Ptr CUChar -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr CUChar
out
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_SIG_BYTES)
xonly :: Context -> Pub -> IO XOnlyPub
xonly :: Context -> Pub -> IO XOnlyPub
xonly (Context Ptr Context
tex) (Pub ByteString
pub) =
Int -> (Ptr XOnlyPublicKey64 -> IO XOnlyPub) -> IO XOnlyPub
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_PUB_BYTES_INTERNAL ((Ptr XOnlyPublicKey64 -> IO XOnlyPub) -> IO XOnlyPub)
-> (Ptr XOnlyPublicKey64 -> IO XOnlyPub) -> IO XOnlyPub
forall a b. (a -> b) -> a -> b
$ \Ptr XOnlyPublicKey64
out ->
ByteString -> (CString -> IO XOnlyPub) -> IO XOnlyPub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
pub ((CString -> IO XOnlyPub) -> IO XOnlyPub)
-> (CString -> IO XOnlyPub) -> IO XOnlyPub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr PubKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr PubKey64
pup) -> do
CInt
_ <- Ptr Context
-> Ptr XOnlyPublicKey64 -> Ptr CInt -> Ptr PubKey64 -> IO CInt
secp256k1_xonly_pubkey_from_pubkey Ptr Context
tex Ptr XOnlyPublicKey64
out Ptr CInt
forall {b}. Ptr b
F.nullPtr Ptr PubKey64
pup
let key :: Ptr b
key = Ptr XOnlyPublicKey64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr XOnlyPublicKey64
out
ByteString
pux <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
key, Int
_PUB_BYTES_INTERNAL)
XOnlyPub -> IO XOnlyPub
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> XOnlyPub
XOnlyPub ByteString
pux)
parse_xonly
:: Context
-> BS.ByteString
-> IO XOnlyPub
parse_xonly :: Context -> ByteString -> IO XOnlyPub
parse_xonly (Context Ptr Context
tex) ByteString
bs =
Int -> (Ptr XOnlyPublicKey64 -> IO XOnlyPub) -> IO XOnlyPub
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_PUB_BYTES_INTERNAL ((Ptr XOnlyPublicKey64 -> IO XOnlyPub) -> IO XOnlyPub)
-> (Ptr XOnlyPublicKey64 -> IO XOnlyPub) -> IO XOnlyPub
forall a b. (a -> b) -> a -> b
$ \Ptr XOnlyPublicKey64
out ->
ByteString -> (CString -> IO XOnlyPub) -> IO XOnlyPub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
bs ((CString -> IO XOnlyPub) -> IO XOnlyPub)
-> (CString -> IO XOnlyPub) -> IO XOnlyPub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr CUChar
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr CUChar
pub) -> do
CInt
suc <- Ptr Context -> Ptr XOnlyPublicKey64 -> Ptr CUChar -> IO CInt
secp256k1_xonly_pubkey_parse Ptr Context
tex Ptr XOnlyPublicKey64
out Ptr CUChar
pub
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let key :: Ptr b
key = Ptr XOnlyPublicKey64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr XOnlyPublicKey64
out
ByteString
pux <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
key, Int
_PUB_BYTES_INTERNAL)
XOnlyPub -> IO XOnlyPub
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> XOnlyPub
XOnlyPub ByteString
pux)
serialize_xonly
:: Context
-> XOnlyPub
-> IO BS.ByteString
serialize_xonly :: Context -> XOnlyPub -> IO ByteString
serialize_xonly (Context Ptr Context
tex) (XOnlyPub ByteString
pux) =
Int -> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_PUB_BYTES_XONLY ((Ptr CUChar -> IO ByteString) -> IO ByteString)
-> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr CUChar
out -> do
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
pux ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr XOnlyPublicKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr XOnlyPublicKey64
pub) -> do
CInt
_ <- Ptr Context -> Ptr CUChar -> Ptr XOnlyPublicKey64 -> IO CInt
secp256k1_xonly_pubkey_serialize Ptr Context
tex Ptr CUChar
out Ptr XOnlyPublicKey64
pub
let enc :: Ptr b
enc = Ptr CUChar -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr CUChar
out
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_PUB_BYTES_XONLY)
keypair
:: Context
-> BS.ByteString
-> IO KeyPair
keypair :: Context -> ByteString -> IO KeyPair
keypair (Context Ptr Context
tex) ByteString
sec
| ByteString -> Int
BS.length ByteString
sec Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO KeyPair
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = Int -> (Ptr KeyPair96 -> IO KeyPair) -> IO KeyPair
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_KEYPAIR_BYTES ((Ptr KeyPair96 -> IO KeyPair) -> IO KeyPair)
-> (Ptr KeyPair96 -> IO KeyPair) -> IO KeyPair
forall a b. (a -> b) -> a -> b
$ \Ptr KeyPair96
out ->
ByteString -> (CString -> IO KeyPair) -> IO KeyPair
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sec ((CString -> IO KeyPair) -> IO KeyPair)
-> (CString -> IO KeyPair) -> IO KeyPair
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr SecKey32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr SecKey32
key) -> do
CInt
suc <- Ptr Context -> Ptr KeyPair96 -> Ptr SecKey32 -> IO CInt
secp256k1_keypair_create Ptr Context
tex Ptr KeyPair96
out Ptr SecKey32
key
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let enc :: Ptr b
enc = Ptr KeyPair96 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr KeyPair96
out
ByteString
per <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_KEYPAIR_BYTES)
KeyPair -> IO KeyPair
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> KeyPair
KeyPair ByteString
per)
keypair_pub :: Context -> KeyPair -> IO Pub
keypair_pub :: Context -> KeyPair -> IO Pub
keypair_pub (Context Ptr Context
tex) (KeyPair ByteString
per) =
Int -> (Ptr PubKey64 -> IO Pub) -> IO Pub
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_PUB_BYTES_INTERNAL ((Ptr PubKey64 -> IO Pub) -> IO Pub)
-> (Ptr PubKey64 -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \Ptr PubKey64
out ->
ByteString -> (CString -> IO Pub) -> IO Pub
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
per ((CString -> IO Pub) -> IO Pub) -> (CString -> IO Pub) -> IO Pub
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr KeyPair96
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr KeyPair96
par) -> do
CInt
_ <- Ptr Context -> Ptr PubKey64 -> Ptr KeyPair96 -> IO CInt
secp256k1_keypair_pub Ptr Context
tex Ptr PubKey64
out Ptr KeyPair96
par
let enc :: Ptr b
enc = Ptr PubKey64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr PubKey64
out
ByteString
pub <- CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_PUB_BYTES_INTERNAL)
Pub -> IO Pub
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (ByteString -> Pub
Pub ByteString
pub)
keypair_sec
:: Context
-> KeyPair
-> IO BS.ByteString
keypair_sec :: Context -> KeyPair -> IO ByteString
keypair_sec (Context Ptr Context
tex) (KeyPair ByteString
per) =
Int -> (Ptr SecKey32 -> IO ByteString) -> IO ByteString
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_SEC_BYTES ((Ptr SecKey32 -> IO ByteString) -> IO ByteString)
-> (Ptr SecKey32 -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr SecKey32
out ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
per ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr KeyPair96
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr KeyPair96
par) -> do
CInt
_ <- Ptr Context -> Ptr SecKey32 -> Ptr KeyPair96 -> IO CInt
secp256k1_keypair_sec Ptr Context
tex Ptr SecKey32
out Ptr KeyPair96
par
let enc :: Ptr b
enc = Ptr SecKey32 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr SecKey32
out
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_SEC_BYTES)
ecdh
:: Context
-> Pub
-> BS.ByteString
-> IO BS.ByteString
ecdh :: Context -> Pub -> ByteString -> IO ByteString
ecdh (Context Ptr Context
tex) (Pub ByteString
pub) ByteString
sec
| ByteString -> Int
BS.length ByteString
sec Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 = Secp256k1Exception -> IO ByteString
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise =
Int -> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_SEC_BYTES ((Ptr CUChar -> IO ByteString) -> IO ByteString)
-> (Ptr CUChar -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr CUChar
out ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
pub ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr PubKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr PubKey64
pup) ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sec ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr SecKey32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr SecKey32
sep) -> do
CInt
suc <- Ptr Context
-> Ptr CUChar
-> Ptr PubKey64
-> Ptr SecKey32
-> Ptr Any
-> Ptr Any
-> IO CInt
forall a b.
Ptr Context
-> Ptr CUChar
-> Ptr PubKey64
-> Ptr SecKey32
-> Ptr a
-> Ptr b
-> IO CInt
secp256k1_ecdh Ptr Context
tex Ptr CUChar
out Ptr PubKey64
pup Ptr SecKey32
sep Ptr Any
forall {b}. Ptr b
F.nullPtr Ptr Any
forall {b}. Ptr b
F.nullPtr
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let key :: Ptr b
key = Ptr CUChar -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr CUChar
out
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
key, Int
_SEC_BYTES)
sign_schnorr
:: Context
-> BS.ByteString
-> BS.ByteString
-> BS.ByteString
-> IO BS.ByteString
sign_schnorr :: Context -> ByteString -> ByteString -> ByteString -> IO ByteString
sign_schnorr c :: Context
c@(Context Ptr Context
tex) ByteString
msg ByteString
sec ByteString
aux
| ByteString -> Int
BS.length ByteString
msg Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 Bool -> Bool -> Bool
|| ByteString -> Int
BS.length ByteString
sec Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 Bool -> Bool -> Bool
|| ByteString -> Int
BS.length ByteString
aux Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 =
Secp256k1Exception -> IO ByteString
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise = Int -> (Ptr Sig64 -> IO ByteString) -> IO ByteString
forall a b. Int -> (Ptr a -> IO b) -> IO b
A.allocaBytes Int
_SIG_BYTES ((Ptr Sig64 -> IO ByteString) -> IO ByteString)
-> (Ptr Sig64 -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \Ptr Sig64
out ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
msg ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr MsgHash32
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr MsgHash32
has) ->
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
aux ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr CUChar
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr CUChar
enn) -> do
KeyPair ByteString
per <- Context -> ByteString -> IO KeyPair
keypair Context
c ByteString
sec
ByteString -> (CString -> IO ByteString) -> IO ByteString
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
per ((CString -> IO ByteString) -> IO ByteString)
-> (CString -> IO ByteString) -> IO ByteString
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr KeyPair96
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr KeyPair96
pur) -> do
CInt
suc <- Ptr Context
-> Ptr Sig64
-> Ptr MsgHash32
-> Ptr KeyPair96
-> Ptr CUChar
-> IO CInt
secp256k1_schnorrsig_sign32 Ptr Context
tex Ptr Sig64
out Ptr MsgHash32
has Ptr KeyPair96
pur Ptr CUChar
enn
Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/= CInt
1) (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ Secp256k1Exception -> IO ()
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
Secp256k1Error
let enc :: Ptr b
enc = Ptr Sig64 -> Ptr b
forall a b. Ptr a -> Ptr b
F.castPtr Ptr Sig64
out
CStringLen -> IO ByteString
BS.packCStringLen (CString
forall {b}. Ptr b
enc, Int
_SIG_BYTES)
verify_schnorr
:: Context
-> Pub
-> BS.ByteString
-> BS.ByteString
-> IO Bool
verify_schnorr :: Context -> Pub -> ByteString -> ByteString -> IO Bool
verify_schnorr c :: Context
c@(Context Ptr Context
tex) Pub
pub ByteString
msg ByteString
sig
| ByteString -> Int
BS.length ByteString
msg Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
32 Bool -> Bool -> Bool
|| ByteString -> Int
BS.length ByteString
sig Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
/= Int
64 = Secp256k1Exception -> IO Bool
forall e a. Exception e => e -> IO a
throwIO Secp256k1Exception
CSecp256k1Error
| Bool
otherwise =
ByteString -> (CString -> IO Bool) -> IO Bool
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
sig ((CString -> IO Bool) -> IO Bool)
-> (CString -> IO Bool) -> IO Bool
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr Sig64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr Sig64
sip) ->
ByteString -> (CStringLen -> IO Bool) -> IO Bool
forall a. ByteString -> (CStringLen -> IO a) -> IO a
BS.useAsCStringLen ByteString
msg ((CStringLen -> IO Bool) -> IO Bool)
-> (CStringLen -> IO Bool) -> IO Bool
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr CUChar
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr CUChar
has, Int -> CSize
forall a b. (Integral a, Num b) => a -> b
fromIntegral -> CSize
len) -> do
XOnlyPub ByteString
pux <- Context -> Pub -> IO XOnlyPub
xonly Context
c Pub
pub
ByteString -> (CString -> IO Bool) -> IO Bool
forall a. ByteString -> (CString -> IO a) -> IO a
BS.useAsCString ByteString
pux ((CString -> IO Bool) -> IO Bool)
-> (CString -> IO Bool) -> IO Bool
forall a b. (a -> b) -> a -> b
$ \(CString -> Ptr XOnlyPublicKey64
forall a b. Ptr a -> Ptr b
F.castPtr -> Ptr XOnlyPublicKey64
pax) -> do
CInt
suc <- Ptr Context
-> Ptr Sig64
-> Ptr CUChar
-> CSize
-> Ptr XOnlyPublicKey64
-> IO CInt
secp256k1_schnorrsig_verify Ptr Context
tex Ptr Sig64
sip Ptr CUChar
has CSize
len Ptr XOnlyPublicKey64
pax
Bool -> IO Bool
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (CInt
suc CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
== CInt
1)