botan-bindings (empty) → 0.0.1.0
raw patch · 48 files changed
+4768/−0 lines, 48 filesdep +basedep +bytestring
Dependencies added: base, bytestring
Files
- CHANGELOG.md +5/−0
- README.md +7/−0
- botan-bindings.cabal +143/−0
- src/Botan/Bindings/Bcrypt.hs +58/−0
- src/Botan/Bindings/BlockCipher.hs +144/−0
- src/Botan/Bindings/Cipher.hsc +229/−0
- src/Botan/Bindings/Error.hsc +113/−0
- src/Botan/Bindings/FPE.hsc +89/−0
- src/Botan/Bindings/HOTP.hs +83/−0
- src/Botan/Bindings/Hash.hs +172/−0
- src/Botan/Bindings/KDF.hs +80/−0
- src/Botan/Bindings/KeyWrap.hs +52/−0
- src/Botan/Bindings/MAC.hs +153/−0
- src/Botan/Bindings/MPI.hs +327/−0
- src/Botan/Bindings/Prelude.hs +66/−0
- src/Botan/Bindings/PubKey.hsc +512/−0
- src/Botan/Bindings/PubKey/DH.hs +35/−0
- src/Botan/Bindings/PubKey/DSA.hs +53/−0
- src/Botan/Bindings/PubKey/Decrypt.hsc +59/−0
- src/Botan/Bindings/PubKey/ECDH.hs +32/−0
- src/Botan/Bindings/PubKey/ECDSA.hs +32/−0
- src/Botan/Bindings/PubKey/Ed25519.hs +40/−0
- src/Botan/Bindings/PubKey/ElGamal.hs +56/−0
- src/Botan/Bindings/PubKey/Encrypt.hsc +61/−0
- src/Botan/Bindings/PubKey/KeyAgreement.hsc +77/−0
- src/Botan/Bindings/PubKey/KeyEncapsulation.hs +102/−0
- src/Botan/Bindings/PubKey/RSA.hs +47/−0
- src/Botan/Bindings/PubKey/SM2.hs +42/−0
- src/Botan/Bindings/PubKey/Sign.hsc +70/−0
- src/Botan/Bindings/PubKey/Verify.hsc +62/−0
- src/Botan/Bindings/PubKey/X25519.hs +40/−0
- src/Botan/Bindings/PwdHash.hs +68/−0
- src/Botan/Bindings/RNG.hs +150/−0
- src/Botan/Bindings/SRP6.hs +117/−0
- src/Botan/Bindings/TOTP.hs +89/−0
- src/Botan/Bindings/Utility.hsc +70/−0
- src/Botan/Bindings/Version.hs +36/−0
- src/Botan/Bindings/View.hs +58/−0
- src/Botan/Bindings/X509.hsc +298/−0
- src/Botan/Bindings/X509/CA.hs +89/−0
- src/Botan/Bindings/X509/CRL.hs +142/−0
- src/Botan/Bindings/X509/CSR.hs +45/−0
- src/Botan/Bindings/X509/DN.hs +56/−0
- src/Botan/Bindings/X509/Extensions.hs +19/−0
- src/Botan/Bindings/X509/Options.hs +152/−0
- src/Botan/Bindings/X509/Path.hs +83/−0
- src/Botan/Bindings/X509/Store.hs +188/−0
- src/Botan/Bindings/ZFEC.hs +67/−0
+ CHANGELOG.md view
@@ -0,0 +1,5 @@+# Changelog++## 0.0.1 - 2024/02/05++Initial release.
+ README.md view
@@ -0,0 +1,7 @@+# Welcome to botan-bindings++Raw bindings to the [Botan](https://botan.randombit.net/) cryptography library.++> Botan's goal is to be the best option for cryptography in C++ by offering the tools necessary to implement a range of practical systems, such as TLS protocol, X.509 certificates, modern AEAD ciphers, PKCS#11 and TPM hardware support, password hashing, and post quantum crypto schemes.++For more information, see the [README on Github](https://github.com/apotheca/botan)
+ botan-bindings.cabal view
@@ -0,0 +1,143 @@+cabal-version: 3.0+name: botan-bindings+version: 0.0.1.0+license: BSD-3-Clause+author: Leo D.+maintainer: leo@apotheca.io+build-type: Simple+category: Cryptography+synopsis: Raw Botan bindings+description:++ Welcome to botan-bindings++ Raw bindings to the [Botan](https://botan.randombit.net/) cryptography library.++ > Botan's goal is to be the best option for cryptography in C++ by offering the+ > tools necessary to implement a range of practical systems, such as TLS protocol,+ > X.509 certificates, modern AEAD ciphers, PKCS#11 and TPM hardware support,+ > password hashing, and post quantum crypto schemes.++ For more information, see the [README on Github](https://github.com/apotheca/botan)++extra-doc-files:+ README.md+ CHANGELOG.md++tested-with:+ -- GHC == 9.0.2,+ GHC == 9.2.8,+ GHC == 9.4.7,+ GHC == 9.6.3,+ GHC == 9.8.1++source-repository head+ type: git+ location: https://github.com/apotheca/botan.git++flag pkg-config+ default: True+ manual: False+ description: Use @pkg-config(1)@ to locate foreign @botan-3@ library.++-- TODO: Probably need a custom Setup.hs for building Botan's C++ / Makefile+-- Would be good to tie this into the extended botan.+-- SEE: https://discourse.haskell.org/t/botan-bindings-devlog/6855/129+-- flag bundled-c-botan+-- default: False+-- manual: True+-- description: Use the bundled botan-3 C/C++ sources.+-- For GHCJS and WASM this is the default.++flag XFFI+ description: Enable experimental / upstream ffi support+ manual: True+ default: False++library+ hs-source-dirs: src+ default-language: Haskell2010+ default-extensions:+ DeriveDataTypeable+ DerivingStrategies+ GeneralizedNewtypeDeriving+ NoImplicitPrelude+ OverloadedStrings+ PatternSynonyms+ RoleAnnotations+ ScopedTypeVariables+ StandaloneKindSignatures+ exposed-modules:+ Botan.Bindings.Bcrypt+ Botan.Bindings.BlockCipher+ Botan.Bindings.Cipher+ Botan.Bindings.Error+ Botan.Bindings.FPE+ Botan.Bindings.Hash+ Botan.Bindings.HOTP+ Botan.Bindings.KDF+ Botan.Bindings.KeyWrap+ Botan.Bindings.MAC+ Botan.Bindings.MPI+ Botan.Bindings.Prelude+ Botan.Bindings.PubKey+ Botan.Bindings.PubKey.Decrypt+ Botan.Bindings.PubKey.DH+ Botan.Bindings.PubKey.DSA+ Botan.Bindings.PubKey.ECDH+ Botan.Bindings.PubKey.ECDSA+ Botan.Bindings.PubKey.Ed25519+ Botan.Bindings.PubKey.ElGamal+ Botan.Bindings.PubKey.Encrypt+ Botan.Bindings.PubKey.KeyAgreement+ Botan.Bindings.PubKey.KeyEncapsulation+ Botan.Bindings.PubKey.RSA+ Botan.Bindings.PubKey.Sign+ Botan.Bindings.PubKey.SM2+ Botan.Bindings.PubKey.Verify+ Botan.Bindings.PubKey.X25519+ Botan.Bindings.PwdHash+ Botan.Bindings.RNG+ Botan.Bindings.SRP6+ Botan.Bindings.TOTP+ Botan.Bindings.Utility+ Botan.Bindings.Version+ Botan.Bindings.View+ Botan.Bindings.X509+ Botan.Bindings.ZFEC+ other-modules:+ Paths_botan_bindings+ autogen-modules:+ Paths_botan_bindings+ build-depends:+ base >= 4 && < 5,+ bytestring >= 0.11 && < 0.13,+ includes:+ botan/ffi.h+ -- TODO Pt2: Bundle a complete copy of the Botan C/C++ source.+ -- if flag(bundled-c-botan) || impl(ghcjs) || os(ghcjs) || arch(wasm32)+ -- c-sources: ...+ -- cxx-sources: ...+ -- include-dirs: ...+ -- else+ -- TODO: Indent after bundling Botan C/C++ source.+ if flag(pkg-config)+ -- NB: pkg-config is available on windows as well when using msys2+ pkgconfig-depends: botan-3 >= 3.0.0+ else+ extra-libraries: botan-3+ -- END TODO: Indent+ -- cc-options: -Wall+ ghc-options: -Wall -Wno-name-shadowing+ if flag(XFFI)+ exposed-modules:+ Botan.Bindings.X509.CA+ Botan.Bindings.X509.CSR+ Botan.Bindings.X509.CRL+ Botan.Bindings.X509.DN+ Botan.Bindings.X509.Extensions+ -- Botan.Bindings.X509.OCSP+ Botan.Bindings.X509.Options+ Botan.Bindings.X509.Path+ Botan.Bindings.X509.Store+ cpp-options: -DXFFI
+ src/Botan/Bindings/Bcrypt.hs view
@@ -0,0 +1,58 @@+{-|+Module : Botan.Bindings.Bcrypt+Description : Bcrypt password hashing+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++Generate and validate Bcrypt password hashes+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.Bcrypt where++import Botan.Bindings.Prelude+import Botan.Bindings.RNG++-- TODO: Maybe move to Botan.Low.Bcrypt+pattern BOTAN_BCRYPT_WORK_FACTOR_FAST+ , BOTAN_BCRYPT_WORK_FACTOR_GOOD+ , BOTAN_BCRYPT_WORK_FACTOR_STRONG+ :: (Eq a, Num a) => a++-- | Should not cause noticable CPU usage+pattern BOTAN_BCRYPT_WORK_FACTOR_FAST = 12++-- | May cause noticable CPU usage+pattern BOTAN_BCRYPT_WORK_FACTOR_GOOD = 14++-- | May block for several seconds+pattern BOTAN_BCRYPT_WORK_FACTOR_STRONG = 16++{- |+Create a password hash using Bcrypt++Output is formatted bcrypt $2a$...+-}+foreign import capi safe "botan/ffi.h botan_bcrypt_generate"+ botan_bcrypt_generate+ :: Ptr Word8 -- ^ __out__: buffer holding the password hash, should be of length 64 bytes+ -> Ptr CSize -- ^ __out_len__: the desired output length in bytes+ -> ConstPtr CChar -- ^ __password__: the password+ -> BotanRNG -- ^ __rng__: a random number generator+ -> CSize -- ^ __work_factor__: how much work to do to slow down guessing attacks+ -> Word32 -- ^ __flags__: should be 0 in current API revision, all other uses are reserved+ -- and return BOTAN_FFI_ERROR_BAD_FLAG+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Check a previously created password hash+foreign import capi safe "botan/ffi.h botan_bcrypt_is_valid"+ botan_bcrypt_is_valid+ :: ConstPtr CChar -- ^ __pass__: the password to check against+ -> ConstPtr CChar -- ^ __hash__: the stored hash to check against+ -> IO CInt -- ^ 0 if if this password/hash combination is valid,+ -- 1 if the combination is not valid (but otherwise well formed),+ -- negative on error
+ src/Botan/Bindings/BlockCipher.hs view
@@ -0,0 +1,144 @@+{-|+Module : Botan.Binding.BlockCipher+Description : Raw Block Cipher (PRP) interface+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++This is a ‘raw’ interface to ECB mode block ciphers.+Most applications want the higher level cipher API which provides authenticated encryption.+This API exists as an escape hatch for applications which need to implement custom primitives using a PRP.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.BlockCipher where++import Botan.Bindings.Prelude++-- | Opaque BlockCipher struct+data {-# CTYPE "botan/ffi.h" "struct botan_block_cipher_struct" #-} BotanBlockCipherStruct++-- | Botan BlockCipher object+newtype {-# CTYPE "botan/ffi.h" "botan_block_cipher_t" #-} BotanBlockCipher+ = MkBotanBlockCipher { runBotanBlockCipher :: Ptr BotanBlockCipherStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a block cipher object+foreign import capi safe "botan/ffi.h &botan_block_cipher_destroy"+ botan_block_cipher_destroy+ :: FinalizerPtr BotanBlockCipherStruct++pattern BOTAN_BLOCK_CIPHER_128_AES_128+ , BOTAN_BLOCK_CIPHER_128_AES_192+ , BOTAN_BLOCK_CIPHER_128_AES_256+ , BOTAN_BLOCK_CIPHER_128_ARIA_128+ , BOTAN_BLOCK_CIPHER_128_ARIA_192+ , BOTAN_BLOCK_CIPHER_128_ARIA_256+ , BOTAN_BLOCK_CIPHER_128_CAMELLIA_128+ , BOTAN_BLOCK_CIPHER_128_CAMELLIA_192+ , BOTAN_BLOCK_CIPHER_128_CAMELLIA_256+ , BOTAN_BLOCK_CIPHER_128_NOEKEON+ , BOTAN_BLOCK_CIPHER_128_SEED+ , BOTAN_BLOCK_CIPHER_128_SM4+ , BOTAN_BLOCK_CIPHER_128_SERPENT+ , BOTAN_BLOCK_CIPHER_128_TWOFISH+ :: (Eq a, IsString a) => a++pattern BOTAN_BLOCK_CIPHER_128_AES_128 = "AES-128"+pattern BOTAN_BLOCK_CIPHER_128_AES_192 = "AES-192"+pattern BOTAN_BLOCK_CIPHER_128_AES_256 = "AES-256"+pattern BOTAN_BLOCK_CIPHER_128_ARIA_128 = "ARIA-128"+pattern BOTAN_BLOCK_CIPHER_128_ARIA_192 = "ARIA-192"+pattern BOTAN_BLOCK_CIPHER_128_ARIA_256 = "ARIA-256"+pattern BOTAN_BLOCK_CIPHER_128_CAMELLIA_128 = "Camellia-128"+pattern BOTAN_BLOCK_CIPHER_128_CAMELLIA_192 = "Camellia-192"+pattern BOTAN_BLOCK_CIPHER_128_CAMELLIA_256 = "Camellia-256"+pattern BOTAN_BLOCK_CIPHER_128_NOEKEON = "Noekeon"+pattern BOTAN_BLOCK_CIPHER_128_SEED = "SEED"+pattern BOTAN_BLOCK_CIPHER_128_SM4 = "SM4"+pattern BOTAN_BLOCK_CIPHER_128_SERPENT = "Serpent"+pattern BOTAN_BLOCK_CIPHER_128_TWOFISH = "Twofish"++pattern BOTAN_BLOCK_CIPHER_BLOWFISH+ , BOTAN_BLOCK_CIPHER_CAST_128+ , BOTAN_BLOCK_CIPHER_DES+ , BOTAN_BLOCK_CIPHER_TRIPLEDES+ , BOTAN_BLOCK_CIPHER_GOST_28147_89+ , BOTAN_BLOCK_CIPHER_IDEA+ , BOTAN_BLOCK_CIPHER_SHACAL2+ , BOTAN_BLOCK_CIPHER_THREEFISH_512+ :: (Eq a, IsString a) => a++pattern BOTAN_BLOCK_CIPHER_BLOWFISH = "Blowfish"+pattern BOTAN_BLOCK_CIPHER_CAST_128 = "CAST-128"+pattern BOTAN_BLOCK_CIPHER_DES = "DES"+pattern BOTAN_BLOCK_CIPHER_TRIPLEDES = "TripleDES"+pattern BOTAN_BLOCK_CIPHER_GOST_28147_89 = "GOST-28147-89"+pattern BOTAN_BLOCK_CIPHER_IDEA = "IDEA"+pattern BOTAN_BLOCK_CIPHER_SHACAL2 = "SHACAL2"+pattern BOTAN_BLOCK_CIPHER_THREEFISH_512 = "Threefish-512"++-- | Initialize a block cipher object+foreign import capi safe "botan/ffi.h botan_block_cipher_init"+ botan_block_cipher_init+ :: Ptr BotanBlockCipher -- ^ __bc__+ -> ConstPtr CChar -- ^ __cipher_name__+ -> IO CInt++-- | Reinitializes the block cipher+foreign import capi safe "botan/ffi.h botan_block_cipher_clear"+ botan_block_cipher_clear+ :: BotanBlockCipher -- ^ __bc__+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Set the key for a block cipher instance+foreign import capi safe "botan/ffi.h botan_block_cipher_set_key"+ botan_block_cipher_set_key+ :: BotanBlockCipher -- ^ __bc__+ -> ConstPtr Word8 -- ^ __key[]__+ -> CSize -- ^ __len__+ -> IO CInt++-- | Return the positive block size of this block cipher, or negative to indicate an error+foreign import capi safe "botan/ffi.h botan_block_cipher_block_size"+ botan_block_cipher_block_size+ :: BotanBlockCipher -- ^ __bc__+ -> IO CInt++-- | Encrypt one or more blocks with the cipher+foreign import capi safe "botan/ffi.h botan_block_cipher_encrypt_blocks"+ botan_block_cipher_encrypt_blocks+ :: BotanBlockCipher -- ^ __bc__+ -> ConstPtr Word8 -- ^ __in[]__+ -> Ptr Word8 -- ^ __out[]__+ -> CSize -- ^ __blocks__+ -> IO CInt++-- | Decrypt one or more blocks with the cipher+foreign import capi safe "botan/ffi.h botan_block_cipher_decrypt_blocks"+ botan_block_cipher_decrypt_blocks+ :: BotanBlockCipher -- ^ __bc__+ -> ConstPtr Word8 -- ^ __in[]__+ -> Ptr Word8 -- ^ __out[]__+ -> CSize -- ^ __blocks__+ -> IO CInt++-- | Get the name of this block cipher+foreign import capi safe "botan/ffi.h botan_block_cipher_name"+ botan_block_cipher_name+ :: BotanBlockCipher -- ^ __cipher__: the object to read+ -> Ptr CChar -- ^ __name__: output buffer+ -> Ptr CSize -- ^ __name_len__: on input, the length of buffer, on success the number of bytes written+ -> IO CInt++-- | Get the key length limits of this block cipher+foreign import capi safe "botan/ffi.h botan_block_cipher_get_keyspec"+ botan_block_cipher_get_keyspec+ :: BotanBlockCipher -- ^ __cipher__: the object to read+ -> Ptr CSize -- ^ __out_minimum_keylength__: if non-NULL, will be set to minimum keylength of cipher+ -> Ptr CSize -- ^ __out_maximum_keylength__: if non-NULL, will be set to maximum keylength of cipher+ -> Ptr CSize -- ^ __out_keylength_modulo__: if non-NULL will be set to byte multiple of valid keys+ -> IO CInt
+ src/Botan/Bindings/Cipher.hsc view
@@ -0,0 +1,229 @@+{-|+Module : Botan.Bindings.Cipher+Description : Symmetric cipher modes+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++A block cipher by itself, is only able to securely encrypt a single+data block. To be able to securely encrypt data of arbitrary length,+a mode of operation applies the block cipher’s single block operation+repeatedly to encrypt an entire message.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.Cipher where++import Botan.Bindings.Prelude++#include <botan/ffi.h>++-- | Opaque Cipher struct+data {-# CTYPE "botan/ffi.h" "struct botan_cipher_struct" #-} BotanCipherStruct++-- | Botan Cipher object+newtype {-# CTYPE "botan/ffi.h" "botan_cipher_t" #-} BotanCipher+ = MkBotanCipher { runBotanCipher :: Ptr BotanCipherStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy the cipher object+foreign import capi safe "botan/ffi.h &botan_cipher_destroy"+ botan_cipher_destroy+ :: FinalizerPtr BotanCipherStruct++pattern BOTAN_CIPHER_MODE_CBC+ , BOTAN_CIPHER_MODE_CFB+ , BOTAN_CIPHER_MODE_XTS+ :: (Eq a, IsString a) => a++pattern BOTAN_CIPHER_MODE_CBC = "CBC"+pattern BOTAN_CIPHER_MODE_CFB = "CFB"+pattern BOTAN_CIPHER_MODE_XTS = "XTS"++pattern BOTAN_CBC_PADDING_PKCS7+ , BOTAN_CBC_PADDING_ONE_AND_ZEROS+ , BOTAN_CBC_PADDING_X9_23+ , BOTAN_CBC_PADDING_ESP+ , BOTAN_CBC_PADDING_CTS+ , BOTAN_CBC_PADDING_NO_PADDING+ :: (Eq a, IsString a) => a++pattern BOTAN_CBC_PADDING_PKCS7 = "PKCS7"+pattern BOTAN_CBC_PADDING_ONE_AND_ZEROS = "OneAndZeros"+pattern BOTAN_CBC_PADDING_X9_23 = "X9.23"+pattern BOTAN_CBC_PADDING_ESP = "ESP"+pattern BOTAN_CBC_PADDING_CTS = "CTS"+pattern BOTAN_CBC_PADDING_NO_PADDING = "NoPadding"++pattern BOTAN_AEAD_CHACHA20POLY1305+ :: (Eq a, IsString a) => a++pattern BOTAN_AEAD_CHACHA20POLY1305 = "ChaCha20Poly1305"++pattern BOTAN_AEAD_MODE_GCM+ , BOTAN_AEAD_MODE_OCB+ , BOTAN_AEAD_MODE_EAX+ , BOTAN_AEAD_MODE_SIV+ , BOTAN_AEAD_MODE_CCM+ :: (Eq a, IsString a) => a++pattern BOTAN_AEAD_MODE_GCM = "GCM"+pattern BOTAN_AEAD_MODE_OCB = "OCB"+pattern BOTAN_AEAD_MODE_EAX = "EAX"+pattern BOTAN_AEAD_MODE_SIV = "SIV"+pattern BOTAN_AEAD_MODE_CCM = "CCM"++pattern BOTAN_CIPHER_INIT_FLAG_MASK_DIRECTION+ , BOTAN_CIPHER_INIT_FLAG_ENCRYPT+ , BOTAN_CIPHER_INIT_FLAG_DECRYPT+ :: (Eq a, Num a) => a+pattern BOTAN_CIPHER_INIT_FLAG_MASK_DIRECTION = #const BOTAN_CIPHER_INIT_FLAG_MASK_DIRECTION+pattern BOTAN_CIPHER_INIT_FLAG_ENCRYPT = #const BOTAN_CIPHER_INIT_FLAG_ENCRYPT+pattern BOTAN_CIPHER_INIT_FLAG_DECRYPT = #const BOTAN_CIPHER_INIT_FLAG_DECRYPT++-- | Initialize a cipher object+foreign import capi safe "botan/ffi.h botan_cipher_init"+ botan_cipher_init+ :: Ptr BotanCipher -- ^ __cipher__+ -> ConstPtr CChar -- ^ __name__+ -> Word32 -- ^ __flags__+ -> IO CInt++-- | Return the name of the cipher object+foreign import capi safe "botan/ffi.h botan_cipher_name"+ botan_cipher_name+ :: BotanCipher -- ^ __cipher__+ -> Ptr CChar -- ^ __name__+ -> Ptr CSize -- ^ __name_len__+ -> IO CInt++-- | Return the output length of this cipher, for a particular input length.+foreign import capi safe "botan/ffi.h botan_cipher_output_length"+ botan_cipher_output_length+ :: BotanCipher -- ^ __cipher__+ -> CSize -- ^ __in_len__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++-- | Return if the specified nonce length is valid for this cipher+-- (0 / SUCCESS if valid, 1 / INVALID_IDENTIFIER if not)+foreign import capi safe "botan/ffi.h botan_cipher_valid_nonce_length"+ botan_cipher_valid_nonce_length+ :: BotanCipher -- ^ __cipher__+ -> CSize -- ^ __nl__+ -> IO CInt++-- | Get the tag length of the cipher (0 for non-AEAD modes)+foreign import capi safe "botan/ffi.h botan_cipher_get_tag_length"+ botan_cipher_get_tag_length+ :: BotanCipher -- ^ __cipher__+ -> Ptr CSize -- ^ __tag_size__+ -> IO CInt++-- | Get the default nonce length of this cipher+foreign import capi safe "botan/ffi.h botan_cipher_get_default_nonce_length"+ botan_cipher_get_default_nonce_length+ :: BotanCipher -- ^ __cipher__+ -> Ptr CSize -- ^ __nl__+ -> IO CInt++-- | Return the update granularity of the cipher;+-- botan_cipher_update must be called with blocks of this size, except for the final.+foreign import capi safe "botan/ffi.h botan_cipher_get_update_granularity"+ botan_cipher_get_update_granularity+ :: BotanCipher -- ^ __cipher__+ -> Ptr CSize -- ^ __ug__+ -> IO CInt++{-+Return the ideal update granularity of the cipher.+This is some multiple of the update granularity,+reflecting possibilities for optimization.+-}+foreign import capi safe "botan/ffi.h botan_cipher_get_ideal_update_granularity"+ botan_cipher_get_ideal_update_granularity+ :: BotanCipher -- ^ __cipher__+ -> Ptr CSize -- ^ __ug__+ -> IO CInt++-- | Get information about the key lengths. Prefer botan_cipher_get_keyspec+foreign import capi safe "botan/ffi.h botan_cipher_query_keylen"+ botan_cipher_query_keylen+ :: BotanCipher -- ^ __cipher__+ -> Ptr CSize -- ^ __out_minimum_keylength__+ -> Ptr CSize -- ^ __out_maximum_keylength__+ -> IO CInt++-- | Get information about the supported key lengths.+foreign import capi safe "botan/ffi.h botan_cipher_get_keyspec"+ botan_cipher_get_keyspec+ :: BotanCipher -- ^ __cipher__+ -> Ptr CSize -- ^ __min_keylen__+ -> Ptr CSize -- ^ __max_keylen__+ -> Ptr CSize -- ^ __mod_keylen__+ -> IO CInt++-- | Set the key for this cipher object+foreign import capi safe "botan/ffi.h botan_cipher_set_key"+ botan_cipher_set_key+ :: BotanCipher -- ^ __cipher__+ -> ConstPtr Word8 -- ^ __key__+ -> CSize -- ^ __key_len__+ -> IO CInt++{-+Reset the message specific state for this cipher.+Without resetting the keys, this resets the nonce, and any state+associated with any message bits that have been processed so far.++It is conceptually equivalent to calling botan_cipher_clear followed+by botan_cipher_set_key with the original key.+-}+foreign import capi safe "botan/ffi.h botan_cipher_reset"+ botan_cipher_reset+ :: BotanCipher -- ^ __cipher__+ -> IO CInt++-- | Set the associated data. Will fail if cipher is not an AEAD+foreign import capi safe "botan/ffi.h botan_cipher_set_associated_data"+ botan_cipher_set_associated_data+ :: BotanCipher -- ^ __cipher__+ -> ConstPtr Word8 -- ^ __ad__+ -> CSize -- ^ __ad_len__+ -> IO CInt++-- | Begin processing a new message using the provided nonce+foreign import capi safe "botan/ffi.h botan_cipher_start"+ botan_cipher_start+ :: BotanCipher -- ^ __cipher__+ -> ConstPtr Word8 -- ^ __nonce__+ -> CSize -- ^ __nonce_len__+ -> IO CInt++pattern BOTAN_CIPHER_UPDATE_FLAG_NONE+ , BOTAN_CIPHER_UPDATE_FLAG_FINAL+ :: (Eq a, Num a) => a+pattern BOTAN_CIPHER_UPDATE_FLAG_NONE = 0+pattern BOTAN_CIPHER_UPDATE_FLAG_FINAL = #const BOTAN_CIPHER_UPDATE_FLAG_FINAL++-- | Encrypt some data+foreign import capi safe "botan/ffi.h botan_cipher_update"+ botan_cipher_update+ :: BotanCipher -- ^ __cipher__+ -> Word32 -- ^ __flags__+ -> Ptr Word8 -- ^ __output[]__+ -> CSize -- ^ __output_size__+ -> Ptr CSize -- ^ __output_written__+ -> ConstPtr Word8 -- ^ __input_bytes[]__+ -> CSize -- ^ __input_size__+ -> Ptr CSize -- ^ __input_consumed__+ -> IO CInt++-- | Reset the key, nonce, AD and all other state on this cipher object+foreign import capi safe "botan/ffi.h botan_cipher_clear"+ botan_cipher_clear+ :: BotanCipher -- ^ __hash__+ -> IO CInt
+ src/Botan/Bindings/Error.hsc view
@@ -0,0 +1,113 @@+{-|+Module : Botan.Bindings.Error+Description : Error codes and exception handling+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++Error values below -10000 are reserved for the application (these can be returned from view functions).+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.Error where++import Botan.Bindings.Prelude++#include <botan/ffi.h>++pattern BOTAN_FFI_SUCCESS+ , BOTAN_FFI_INVALID_VERIFIER+ , BOTAN_FFI_ERROR_INVALID_INPUT+ , BOTAN_FFI_ERROR_BAD_MAC+ , BOTAN_FFI_ERROR_INSUFFICIENT_BUFFER_SPACE+ , BOTAN_FFI_ERROR_STRING_CONVERSION_ERROR+ , BOTAN_FFI_ERROR_EXCEPTION_THROWN+ , BOTAN_FFI_ERROR_OUT_OF_MEMORY+ , BOTAN_FFI_ERROR_SYSTEM_ERROR+ , BOTAN_FFI_ERROR_INTERNAL_ERROR+ , BOTAN_FFI_ERROR_BAD_FLAG+ , BOTAN_FFI_ERROR_NULL_POINTER+ , BOTAN_FFI_ERROR_BAD_PARAMETER+ , BOTAN_FFI_ERROR_KEY_NOT_SET+ , BOTAN_FFI_ERROR_INVALID_KEY_LENGTH+ , BOTAN_FFI_ERROR_INVALID_OBJECT_STATE+ , BOTAN_FFI_ERROR_NOT_IMPLEMENTED+ , BOTAN_FFI_ERROR_INVALID_OBJECT+ , BOTAN_FFI_ERROR_TLS_ERROR+ , BOTAN_FFI_ERROR_HTTP_ERROR+ , BOTAN_FFI_ERROR_ROUGHTIME_ERROR+ , BOTAN_FFI_ERROR_UNKNOWN_ERROR+ :: (Eq a, Num a) => a++-- | Generally returned to indicate success+pattern BOTAN_FFI_SUCCESS = #const BOTAN_FFI_SUCCESS++-- | NOTE: this value is positive, but still represents an error condition. In indicates that the function completed successfully, but the value provided was not correct. For example botan_bcrypt_is_valid returns this value if the password did not match the hash.+pattern BOTAN_FFI_INVALID_VERIFIER = #const BOTAN_FFI_INVALID_VERIFIER++-- | The input was invalid. (Currently this error return is not used.)+pattern BOTAN_FFI_ERROR_INVALID_INPUT = #const BOTAN_FFI_ERROR_INVALID_INPUT++-- | While decrypting in an AEAD mode, the tag failed to verify.+pattern BOTAN_FFI_ERROR_BAD_MAC = #const BOTAN_FFI_ERROR_BAD_MAC++-- | Functions which write a variable amount of space return this if the indicated buffer length was insufficient to write the data. In that case, the output length parameter is set to the size that is required.+pattern BOTAN_FFI_ERROR_INSUFFICIENT_BUFFER_SPACE = #const BOTAN_FFI_ERROR_INSUFFICIENT_BUFFER_SPACE++-- | A string view function which attempts to convert a string to a specified charset, and fails, can use this function to indicate the error.+pattern BOTAN_FFI_ERROR_STRING_CONVERSION_ERROR = #const BOTAN_FFI_ERROR_STRING_CONVERSION_ERROR++-- | An exception was thrown while processing this request, but no further details are available.+pattern BOTAN_FFI_ERROR_EXCEPTION_THROWN = #const BOTAN_FFI_ERROR_EXCEPTION_THROWN++-- | Memory allocation failed+pattern BOTAN_FFI_ERROR_OUT_OF_MEMORY = #const BOTAN_FFI_ERROR_OUT_OF_MEMORY++-- | A system call failed+pattern BOTAN_FFI_ERROR_SYSTEM_ERROR = #const BOTAN_FFI_ERROR_SYSTEM_ERROR++-- | An internal bug was encountered (please open a ticket on github)+pattern BOTAN_FFI_ERROR_INTERNAL_ERROR = #const BOTAN_FFI_ERROR_INTERNAL_ERROR++-- | A value provided in a flag variable was unknown.+pattern BOTAN_FFI_ERROR_BAD_FLAG = #const BOTAN_FFI_ERROR_BAD_FLAG++-- | A null pointer was provided as an argument where that is not allowed.+pattern BOTAN_FFI_ERROR_NULL_POINTER = #const BOTAN_FFI_ERROR_NULL_POINTER++-- | An argument did not match the function.+pattern BOTAN_FFI_ERROR_BAD_PARAMETER = #const BOTAN_FFI_ERROR_BAD_PARAMETER++-- | An object that requires a key normally must be keyed before use (eg before encrypting or MACing data). If this is not done, the operation will fail and return this error code.+pattern BOTAN_FFI_ERROR_KEY_NOT_SET = #const BOTAN_FFI_ERROR_KEY_NOT_SET++-- | An invalid key length was provided with a call to foo_set_key.+pattern BOTAN_FFI_ERROR_INVALID_KEY_LENGTH = #const BOTAN_FFI_ERROR_INVALID_KEY_LENGTH++-- | An operation was invoked that makes sense for the object, but it is in the wrong state to perform it.+pattern BOTAN_FFI_ERROR_INVALID_OBJECT_STATE = #const BOTAN_FFI_ERROR_INVALID_OBJECT_STATE++-- | This is returned if the functionality is not available for some reason. For example if you call botan_hash_init with a named hash function which is not enabled, this error is returned.+pattern BOTAN_FFI_ERROR_NOT_IMPLEMENTED = #const BOTAN_FFI_ERROR_NOT_IMPLEMENTED++-- | This is used if an object provided did not match the function. For example calling botan_hash_destroy on a botan_rng_t object will cause this error.+pattern BOTAN_FFI_ERROR_INVALID_OBJECT = #const BOTAN_FFI_ERROR_INVALID_OBJECT++pattern BOTAN_FFI_ERROR_TLS_ERROR = #const BOTAN_FFI_ERROR_TLS_ERROR+pattern BOTAN_FFI_ERROR_HTTP_ERROR = #const BOTAN_FFI_ERROR_HTTP_ERROR+pattern BOTAN_FFI_ERROR_ROUGHTIME_ERROR = #const BOTAN_FFI_ERROR_ROUGHTIME_ERROR++-- | Something bad happened, but we are not sure why or how.+pattern BOTAN_FFI_ERROR_UNKNOWN_ERROR = #const BOTAN_FFI_ERROR_UNKNOWN_ERROR++foreign import capi safe "botan/ffi.h botan_error_description"+ botan_error_description+ :: CInt -- ^ __err__+ -> IO (ConstPtr CChar)++foreign import capi safe "botan/ffi.h botan_error_last_exception_message"+ botan_error_last_exception_message+ :: IO (ConstPtr CChar)
+ src/Botan/Bindings/FPE.hsc view
@@ -0,0 +1,89 @@+{-|+Module : Botan.Bindings.FPE+Description : Format Preserving Encryption+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++Format preserving encryption (FPE) refers to a set of techniques+for encrypting data such that the ciphertext has the same format+as the plaintext. For instance, you can use FPE to encrypt credit+card numbers with valid checksums such that the ciphertext is also+an credit card number with a valid checksum, or similarly for bank+account numbers, US Social Security numbers, or even more general+mappings like English words onto other English words.++The scheme currently implemented in botan is called FE1, and described+in the paper Format Preserving Encryption by Mihir Bellare, Thomas+Ristenpart, Phillip Rogaway, and Till Stegers. FPE is an area of+ongoing standardization and it is likely that other schemes will be+included in the future.++To encrypt an arbitrary value using FE1, you need to use a ranking+method. Basically, the idea is to assign an integer to every value+you might encrypt. For instance, a 16 digit credit card number consists+of a 15 digit code plus a 1 digit checksum. So to encrypt a credit card+number, you first remove the checksum, encrypt the 15 digit value modulo+1015, and then calculate what the checksum is for the new (ciphertext)+number. Or, if you were encrypting words in a dictionary, you could rank+the words by their lexicographical order, and choose the modulus to be+the number of words in the dictionary.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.FPE where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude++#include <botan/ffi.h>++-- | Opaque FPE struct+data {-# CTYPE "botan/ffi.h" "struct botan_fpe_struct" #-} BotanFPEStruct++-- | Botan FPE object+newtype {-# CTYPE "botan/ffi.h" "botan_fpe_t" #-} BotanFPE+ = MkBotanFPE { runBotanFPE :: Ptr BotanFPEStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy the FPE object+foreign import capi safe "botan/ffi.h &botan_fpe_destroy"+ botan_fpe_destroy+ :: FinalizerPtr BotanFPEStruct++pattern BOTAN_FPE_FLAG_NONE + , BOTAN_FPE_FLAG_FE1_COMPAT_MODE+ :: (Eq a, Num a) => a++-- Not an actual flag+pattern BOTAN_FPE_FLAG_NONE = 0+pattern BOTAN_FPE_FLAG_FE1_COMPAT_MODE = #const BOTAN_FPE_FLAG_FE1_COMPAT_MODE++foreign import capi safe "botan/ffi.h botan_fpe_fe1_init"+ botan_fpe_fe1_init+ :: Ptr BotanFPE -- ^ __fpe__+ -> BotanMP -- ^ __n__+ -> ConstPtr Word8 -- ^ __key[]__+ -> CSize -- ^ __key_len__+ -> CSize -- ^ __rounds__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_fpe_encrypt"+ botan_fpe_encrypt+ :: BotanFPE -- ^ __fpe__+ -> BotanMP -- ^ __x__+ -> ConstPtr Word8 -- ^ __tweak[]__+ -> CSize -- ^ __tweak_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_fpe_decrypt"+ botan_fpe_decrypt+ :: BotanFPE -- ^ __fpe__+ -> BotanMP -- ^ __x__+ -> ConstPtr Word8 -- ^ __tweak[]__+ -> CSize -- ^ __tweak_len__+ -> IO CInt
+ src/Botan/Bindings/HOTP.hs view
@@ -0,0 +1,83 @@+{-|+Module : Botan.Bindings.HOTP+Description : Hash-based one-time passwords+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++One time password schemes are a user authentication method that+relies on a fixed secret key which is used to derive a sequence+of short passwords, each of which is accepted only once. Commonly+this is used to implement two-factor authentication (2FA), where+the user authenticates using both a conventional password (or a+public key signature) and an OTP generated by a small device such+as a mobile phone.++Botan implements the HOTP and TOTP schemes from RFC 4226 and 6238.++Since the range of possible OTPs is quite small, applications must+rate limit OTP authentication attempts to some small number per +second. Otherwise an attacker could quickly try all 1000000 6-digit+OTPs in a brief amount of time.++HOTP generates OTPs that are a short numeric sequence, between 6+and 8 digits (most applications use 6 digits), created using the+HMAC of a 64-bit counter value. If the counter ever repeats the+OTP will also repeat, thus both parties must assure the counter+only increments and is never repeated or decremented. Thus both+client and server must keep track of the next counter expected.++Anyone with access to the client-specific secret key can authenticate+as that client, so it should be treated with the same security+consideration as would be given to any other symmetric key or+plaintext password.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.HOTP where+import Botan.Bindings.Prelude++-- | Opaque HOTP struct+data {-# CTYPE "botan/ffi.h" "struct botan_hotp_struct" #-} BotanHOTPStruct++-- | Botan HOTP object+newtype {-# CTYPE "botan/ffi.h" "botan_hotp_t" #-} BotanHOTP+ = MkBotanHOTP { runBotanHOTP :: Ptr BotanHOTPStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a HOTP instance+foreign import capi safe "botan/ffi.h &botan_hotp_destroy"+ botan_hotp_destroy+ :: FinalizerPtr BotanHOTPStruct++-- | Initialize a HOTP instance+foreign import capi safe "botan/ffi.h botan_hotp_init"+ botan_hotp_init+ :: Ptr BotanHOTP -- ^ __hotp__+ -> ConstPtr Word8 -- ^ __key[]__+ -> CSize -- ^ __key_len__+ -> ConstPtr CChar -- ^ __hash_algo__+ -> CSize -- ^ __digits__+ -> IO CInt+++-- | Generate a HOTP code for the provided counter+foreign import capi safe "botan/ffi.h botan_hotp_generate"+ botan_hotp_generate+ :: BotanHOTP -- ^ __hotp__+ -> Ptr Word32 -- ^ __hotp_code__+ -> Word64 -- ^ __hotp_counter__+ -> IO CInt++-- | Verify a HOTP code+foreign import capi safe "botan/ffi.h botan_hotp_check"+ botan_hotp_check+ :: BotanHOTP -- ^ __hotp__+ -> Ptr Word64 -- ^ __next_hotp_counter__+ -> Word32 -- ^ __hotp_code__+ -> Word64 -- ^ __hotp_counter__+ -> CSize -- ^ __resync_range__+ -> IO CInt
+ src/Botan/Bindings/Hash.hs view
@@ -0,0 +1,172 @@+{-|+Module : Botan.Bindings.Hash+Description : Hash Functions and Checksums+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++Hash functions are one-way functions, which map data of arbitrary size+to a fixed output length. Most of the hash functions in Botan are designed+to be cryptographically secure, which means that it is computationally+infeasible to create a collision (finding two inputs with the same hash)+or preimages (given a hash output, generating an arbitrary input with the+same hash). But note that not all such hash functions meet their goals,+in particular MD4 and MD5 are trivially broken. However they are still+included due to their wide adoption in various protocols.++Using a hash function is typically split into three stages: initialization,+update, and finalization (often referred to as a IUF interface). The+initialization stage is implicit: after creating a hash function object,+it is ready to process data. Then update is called one or more times.+Calling update several times is equivalent to calling it once with all of+the arguments concatenated. After completing a hash computation (eg using+hashFinal), the internal state is reset to begin hashing a new message.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.Hash where++import Botan.Bindings.Prelude++-- | Opaque Hash struct+data {-# CTYPE "botan/ffi.h" "struct botan_hash_struct" #-} BotanHashStruct++-- | Botan Hash object+newtype {-# CTYPE "botan/ffi.h" "botan_hash_t" #-} BotanHash+ = MkBotanHash { runBotanHash :: Ptr BotanHashStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Frees all resources of the hash object+foreign import capi safe "botan/ffi.h &botan_hash_destroy"+ botan_hash_destroy+ :: FinalizerPtr BotanHashStruct++pattern BOTAN_HASH_BLAKE2B+ , BOTAN_HASH_KECCAK_1600+ , BOTAN_HASH_GOST_34_11+ , BOTAN_HASH_MD4+ , BOTAN_HASH_MD5+ , BOTAN_HASH_RIPEMD_160+ , BOTAN_HASH_SHA1+ , BOTAN_HASH_SHA_224+ , BOTAN_HASH_SHA_256+ , BOTAN_HASH_SHA_384+ , BOTAN_HASH_SHA_512+ , BOTAN_HASH_SHA_512_256+ , BOTAN_HASH_SHA_3+ , BOTAN_HASH_SHAKE_128+ , BOTAN_HASH_SHAKE_256+ , BOTAN_HASH_SM3+ , BOTAN_HASH_SKEIN_512+ , BOTAN_HASH_STREEBOG_256+ , BOTAN_HASH_STREEBOG_512+ , BOTAN_HASH_WHIRLPOOL+ , BOTAN_HASH_STRAT_PARALLEL+ , BOTAN_HASH_STRAT_COMB4P+ , BOTAN_CHECKSUM_ADLER32+ , BOTAN_CHECKSUM_CRC24+ , BOTAN_CHECKSUM_CRC32+ :: (Eq a, IsString a) => a+pattern BOTAN_HASH_BLAKE2B = "BLAKE2b"+pattern BOTAN_HASH_KECCAK_1600 = "Keccak-1600"+pattern BOTAN_HASH_GOST_34_11 = "GOST-34.11"+pattern BOTAN_HASH_MD4 = "MD4"+pattern BOTAN_HASH_MD5 = "MD5"+pattern BOTAN_HASH_RIPEMD_160 = "RIPEMD-160"+pattern BOTAN_HASH_SHA1 = "SHA-1"+pattern BOTAN_HASH_SHA_224 = "SHA-224"+pattern BOTAN_HASH_SHA_256 = "SHA-256"+pattern BOTAN_HASH_SHA_384 = "SHA-384"+pattern BOTAN_HASH_SHA_512 = "SHA-512"+pattern BOTAN_HASH_SHA_512_256 = "SHA-512-256"+pattern BOTAN_HASH_SHA_3 = "SHA-3"+pattern BOTAN_HASH_SHAKE_128 = "SHAKE-128"+pattern BOTAN_HASH_SHAKE_256 = "SHAKE-256"+pattern BOTAN_HASH_SM3 = "SM3"+pattern BOTAN_HASH_SKEIN_512 = "Skein-512"+pattern BOTAN_HASH_STREEBOG_256 = "Streebog-256"+pattern BOTAN_HASH_STREEBOG_512 = "Streebog-512"+pattern BOTAN_HASH_WHIRLPOOL = "Whirlpool"+-- Combination strategies+pattern BOTAN_HASH_STRAT_PARALLEL = "Parallel"+pattern BOTAN_HASH_STRAT_COMB4P = "Comb4P"+-- Checksums+pattern BOTAN_CHECKSUM_ADLER32 = "Adler32"+pattern BOTAN_CHECKSUM_CRC24 = "CRC24"+pattern BOTAN_CHECKSUM_CRC32 = "CRC32"++-- | Initialize a hash function object+foreign import capi safe "botan/ffi.h botan_hash_init"+ botan_hash_init+ :: Ptr BotanHash -- ^ __hash__: hash object+ -> ConstPtr CChar -- ^ __hash_name__: name of the hash function, e.g., "SHA-384"+ -> Word32 -- ^ __flags__: should be 0 in current API revision, all other uses are reserved+ -- and return BOTAN_FFI_ERROR_BAD_FLAG+ -> IO CInt ++-- | Get the name of this hash function+foreign import capi safe "botan/ffi.h botan_hash_name"+ botan_hash_name+ :: BotanHash -- ^ __hash__: the object to read+ -> Ptr CChar -- ^ __name__: output buffer+ -> Ptr CSize -- ^ __name_len__: on input, the length of buffer, on success the number of bytes written+ -> IO CInt++-- | Copy the state of a hash function object+foreign import capi safe "botan/ffi.h botan_hash_copy_state"+ botan_hash_copy_state+ :: Ptr BotanHash -- ^ __dest__: destination hash object+ -> BotanHash -- ^ __source__: source hash object+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Writes the output length of the hash function to *output_length+foreign import capi safe "botan/ffi.h botan_hash_output_length"+ botan_hash_output_length+ :: BotanHash -- ^ __hash__: hash object+ -> Ptr CSize -- ^ __output_length__: output buffer to hold the hash function output length+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Writes the block size of the hash function to *block_size+foreign import capi safe "botan/ffi.h botan_hash_block_size"+ botan_hash_block_size+ :: BotanHash -- ^ __hash__: hash object+ -> Ptr CSize -- ^ __block_size__: output buffer to hold the hash function block size+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Send more input to the hash function+foreign import capi safe "botan/ffi.h botan_hash_update"+ botan_hash_update+ :: BotanHash -- ^ __hash__: hash object+ -> ConstPtr Word8 -- ^ __in__: input buffer+ -> CSize -- ^ __in_len__: number of bytes to read from the input buffer+ -> IO CInt -- ^ 0 on success, a negative value on failure++{- |+Finalizes the hash computation and writes the output to+out[0:botan_hash_output_length()] then reinitializes for computing+another digest as if botan_hash_clear had been called.+-}+foreign import capi safe "botan/ffi.h botan_hash_final"+ botan_hash_final+ :: BotanHash -- ^ __hash__: hash object+ -> Ptr Word8 -- ^ __out[]__: output buffer+ -> IO CInt -- ^ 0 on success, a negative value on failure++{- |+Reinitializes the state of the hash computation. A hash can+be computed (with update/final) immediately.+-}+foreign import capi safe "botan/ffi.h botan_hash_clear"+ botan_hash_clear+ :: BotanHash -- ^ __hash__: hash object+ -> IO CInt -- 0 on success, a negative value on failure++foreign import capi safe "botan/ffi.h botan_pkcs_hash_id"+ botan_pkcs_hash_id+ :: ConstPtr CChar -- ^ __hash_name__+ -> Ptr Word8 -- ^ __pkcs_id[]__+ -> Ptr CSize -- ^ __pkcs_id_len__+ -> IO CInt
+ src/Botan/Bindings/KDF.hs view
@@ -0,0 +1,80 @@+{-|+Module : Botan.Bindings.KDF+Description : Key Derivation Functions (KDF)+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++Key derivation functions are used to turn some amount of shared+secret material into uniform random keys suitable for use with+symmetric algorithms. An example of an input which is useful for+a KDF is a shared secret created using Diffie-Hellman key agreement.++Typically a KDF is also used with a salt and a label. The salt should+be some random information which is available to all of the parties+that would need to use the KDF; this could be performed by setting+the salt to some kind of session identifier, or by having one of the+parties generate a random salt and including it in a message.++The label is used to bind the KDF output to some specific context. For+instance if you were using the KDF to derive a specific key referred to+as the “message key” in the protocol description, you might use a label+of “FooProtocol v2 MessageKey”. This labeling ensures that if you+accidentally use the same input key and salt in some other context, you+still use different keys in the two contexts.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.KDF where++import Botan.Bindings.Prelude++pattern BOTAN_KDF_HKDF+ , BOTAN_KDF_HKDF_EXTRACT+ , BOTAN_KDF_HKDF_EXPAND+ , BOTAN_KDF_KDF2+ , BOTAN_KDF_KDF1_18033+ , BOTAN_KDF_KDF1+ , BOTAN_KDF_TLS_12_PRF+ , BOTAN_KDF_X9_42_PRF+ , BOTAN_KDF_SP800_108_COUNTER+ , BOTAN_KDF_SP800_108_FEEDBACK+ , BOTAN_KDF_SP800_108_PIPELINE+ , BOTAN_KDF_SP800_56A+ , BOTAN_KDF_SP800_56C+ :: (Eq a, IsString a) => a+ +-- NOTE: All KDFs take a HashName or HMAC(HashName) as an argument+pattern BOTAN_KDF_HKDF = "HKDF"+pattern BOTAN_KDF_HKDF_EXTRACT = "HKDF-Extract"+pattern BOTAN_KDF_HKDF_EXPAND = "HKDF-Expand"+pattern BOTAN_KDF_KDF2 = "KDF2"+pattern BOTAN_KDF_KDF1_18033 = "KDF1-18033"+pattern BOTAN_KDF_KDF1 = "KDF1"+pattern BOTAN_KDF_TLS_12_PRF = "TLS-12-PRF"+-- NOTE: X9_42_PRF is only supposed to take "SHA-1" as an argument+pattern BOTAN_KDF_X9_42_PRF = "X9.42-PRF"+-- NOTE: SP800 inner content should also be wrapped in HMAC, eg:+-- BOTAN_KDF_SP800_56A \$ BOTAN_MAC_HMAC \$ someHash+pattern BOTAN_KDF_SP800_108_COUNTER = "SP800-108-Counter"+pattern BOTAN_KDF_SP800_108_FEEDBACK = "SP800-108-Feedback"+pattern BOTAN_KDF_SP800_108_PIPELINE = "SP800-108-Pipeline"+pattern BOTAN_KDF_SP800_56A = "SP800-56A"+pattern BOTAN_KDF_SP800_56C = "SP800-56C"++-- | Derive a key+foreign import capi safe "botan/ffi.h botan_kdf"+ botan_kdf+ :: ConstPtr CChar -- ^ __kdf_algo__: KDF algorithm, e.g., "SP800-56C"+ -> Ptr Word8 -- ^ __out[]__: buffer holding the derived key, must be of length out_len+ -> CSize -- ^ __out_len__: the desired output length in bytes+ -> ConstPtr Word8 -- ^ __secret[]__: the secret input+ -> CSize -- ^ __secret_len__: size of secret in bytes+ -> ConstPtr Word8 -- ^ __salt[]__: a diversifier+ -> CSize -- ^ __salt_len__: size of salt in bytes+ -> ConstPtr Word8 -- ^ __label[]__: purpose for the derived keying material+ -> CSize -- ^ __label_len__: size of label in bytes+ -> IO CInt -- ^ 0 on success, a negative value on failure
+ src/Botan/Bindings/KeyWrap.hs view
@@ -0,0 +1,52 @@+{-|+Module : Botan.Bindings.KeyWrap+Description : Bcrypt password hashing+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++NIST specifies two mechanisms for wrapping (encrypting) symmetric keys+using another key. The first (and older, more widely supported) method+requires the input be a multiple of 8 bytes long. The other allows any+length input, though only up to 2**32 bytes.++These algorithms are described in NIST SP 800-38F, and RFCs 3394 and 5649.++These functions take an arbitrary 128-bit block cipher. NIST only allows+these functions with AES, but any 128-bit cipher will do and some other+implementations (such as in OpenSSL) do also allow other ciphers.++Use AES for best interop.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.KeyWrap where++import Botan.Bindings.Prelude++foreign import capi safe "botan/ffi.h botan_nist_kw_enc"+ botan_nist_kw_enc+ :: ConstPtr CChar -- ^ __cipher_algo__+ -> CInt -- ^ __padded__+ -> ConstPtr Word8 -- ^ __key[]__+ -> CSize -- ^ __key_len__+ -> ConstPtr Word8 -- ^ __kek[]__+ -> CSize -- ^ __kek_len__+ -> Ptr Word8 -- ^ __wrapped_key[]__+ -> Ptr CSize -- ^ __wrapped_key_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_nist_kw_dec"+ botan_nist_kw_dec+ :: ConstPtr CChar -- ^ __cipher_algo__+ -> CInt -- ^ __padded__+ -> ConstPtr Word8 -- ^ __wrapped_key[]__+ -> CSize -- ^ __wrapped_key_len__+ -> ConstPtr Word8 -- ^ __kek[]__+ -> CSize -- ^ __kek_len__+ -> Ptr Word8 -- ^ __key[]__+ -> Ptr CSize -- ^ __key_len__+ -> IO CInt
+ src/Botan/Bindings/MAC.hs view
@@ -0,0 +1,153 @@+{-|+Module : Botan.Bindings.MAC+Description : Message Authentication Codes (MAC)+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++A Message Authentication Code algorithm computes a tag over a+message utilizing a shared secret key. Thus a valid tag confirms+the authenticity and integrity of the message. Only entities in+possession of the shared secret key are able to verify the tag.++Note++When combining a MAC with unauthenticated encryption mode, prefer+to first encrypt the message and then MAC the ciphertext. The+alternative is to MAC the plaintext, which depending on exact usage+can suffer serious security issues. For a detailed discussion of+this issue see the paper “The Order of Encryption and Authentication+for Protecting Communications” by Hugo Krawczyk++The Botan MAC computation is split into five stages.++- Instantiate the MAC algorithm.++- Set the secret key.++- Process IV.++- Process data.++- Finalize the MAC computation.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.MAC where++import Botan.Bindings.Prelude++-- | Opaque MAC struct+data {-# CTYPE "botan/ffi.h" "struct botan_mac_struct" #-} BotanMACStruct++-- | Botan MAC object+newtype {-# CTYPE "botan/ffi.h" "botan_mac_t" #-} BotanMAC+ = MkBotanMAC { runBotanMAC :: Ptr BotanMACStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Frees all resources of the MAC object+foreign import capi safe "botan/ffi.h &botan_mac_destroy"+ botan_mac_destroy+ :: FinalizerPtr BotanMACStruct++pattern BOTAN_MAC_CMAC+ , BOTAN_MAC_GMAC+ -- , BOTAN_MAC_CBC_MAC+ , BOTAN_MAC_HMAC+ -- , BOTAN_MAC_KMAC_128+ -- , BOTAN_MAC_KMAC_256+ , BOTAN_MAC_Poly1305+ , BOTAN_MAC_SipHash+ , BOTAN_MAC_X9_19_MAC+ :: (Eq a, IsString a) => a++pattern BOTAN_MAC_CMAC = "CMAC"+pattern BOTAN_MAC_GMAC = "GMAC"+-- pattern BOTAN_MAC_CBC_MAC = "CBC-MAC"+pattern BOTAN_MAC_HMAC = "HMAC"+-- pattern BOTAN_MAC_KMAC_128 = ...+-- pattern BOTAN_MAC_KMAC_256 = ...+pattern BOTAN_MAC_Poly1305 = "Poly1305"+pattern BOTAN_MAC_SipHash = "SipHash"+pattern BOTAN_MAC_X9_19_MAC = "X9.19-MAC"++-- | Initialize a message authentication code object+foreign import capi safe "botan/ffi.h botan_mac_init"+ botan_mac_init+ :: Ptr BotanMAC -- ^ __mac__: mac object+ -> ConstPtr CChar -- ^ __mac_name__: name of the hash function, e.g., "HMAC(SHA-384)"+ -> Word32 -- ^ __flags__: should be 0 in current API revision, all other uses are reserved+ -- and return a negative value (error code)+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Writes the output length of the message authentication code to *output_length+foreign import capi safe "botan/ffi.h botan_mac_output_length"+ botan_mac_output_length+ :: BotanMAC -- ^ __mac__: mac object+ -> Ptr CSize -- ^ __output_length__: output buffer to hold the MAC output length+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Sets the key on the MAC+foreign import capi safe "botan/ffi.h botan_mac_set_key"+ botan_mac_set_key+ :: BotanMAC -- ^ __mac__: mac object+ -> ConstPtr Word8 -- ^ __key__: buffer holding the key+ -> CSize -- ^ __key_len__: size of the key buffer in bytes+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Sets the nonce on the MAC+foreign import capi safe "botan/ffi.h botan_mac_set_nonce"+ botan_mac_set_nonce+ :: BotanMAC -- ^ __mac__: mac object+ -> ConstPtr Word8 -- ^ __nonce__: buffer holding the nonce+ -> CSize -- ^ __nonce_len__: size of the nonce buffer in bytes+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Send more input to the message authentication code+foreign import capi safe "botan/ffi.h botan_mac_update"+ botan_mac_update+ :: BotanMAC -- ^ __mac__: mac object+ -> ConstPtr Word8 -- ^ __buf__: input buffer+ -> CSize -- ^ __len__: number of bytes to read from the input buffer+ -> IO CInt -- ^ 0 on success, a negative value on failure++{- |+Finalizes the MAC computation and writes the output to+out[0:botan_mac_output_length()] then reinitializes for computing+another MAC as if botan_mac_clear had been called.+-}+foreign import capi safe "botan/ffi.h botan_mac_final"+ botan_mac_final+ :: BotanMAC -- ^ __mac__: mac object+ -> Ptr Word8 -- ^ __out[]__: output buffer+ -> IO CInt -- ^ 0 on success, a negative value on failure++{- |+Reinitializes the state of the MAC computation. A MAC can+be computed (with update/final) immediately.+-}+foreign import capi safe "botan/ffi.h botan_mac_clear"+ botan_mac_clear+ :: BotanMAC -- ^ __mac__: mac object+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Get the name of this MAC+foreign import capi safe "botan/ffi.h botan_mac_name"+ botan_mac_name+ :: BotanMAC -- ^ __mac__: the object to read+ -> Ptr CChar -- ^ __name__: output buffer+ -> Ptr CSize -- ^ __name_len__: on input, the length of buffer, on success the number of bytes written+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Get the key length limits of this auth code+foreign import capi safe "botan/ffi.h botan_mac_get_keyspec"+ botan_mac_get_keyspec+ :: BotanMAC -- ^ __mac__: the object to read+ -> Ptr CSize -- ^ __out_minimum_keylength__: if non-NULL, will be set to minimum keylength of MAC+ -> Ptr CSize -- ^ __out_maximum_keylength__: if non-NULL, will be set to maximum keylength of MAC+ -> Ptr CSize -- ^ __out_keylength_modulo__: if non-NULL will be set to byte multiple of valid keys+ -> IO CInt -- ^ 0 on success, a negative value on failure+
+ src/Botan/Bindings/MPI.hs view
@@ -0,0 +1,327 @@+{-|+Module : Botan.Bindings.MPI+Description : Multiple Precision Integers+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.MPI where++import Botan.Bindings.Prelude+import Botan.Bindings.RNG++-- | Opaque MP struct+data {-# CTYPE "botan/ffi.h" "struct botan_mp_struct" #-} BotanMPStruct++-- | Botan MP object+newtype {-# CTYPE "botan/ffi.h" "botan_mp_t" #-} BotanMP+ = MkBotanMP { runBotanMP :: Ptr BotanMPStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy (deallocate) an MPI+foreign import capi safe "botan/ffi.h &botan_mp_destroy"+ botan_mp_destroy+ :: FinalizerPtr BotanMPStruct++-- | Initialize an MPI+foreign import capi safe "botan/ffi.h botan_mp_init"+ botan_mp_init+ :: Ptr BotanMP -- ^ __mp__+ -> IO CInt++-- | Convert the MPI to a hex string. Writes botan_mp_num_bytes(mp)*2 + 1 bytes+foreign import capi safe "botan/ffi.h botan_mp_to_hex"+ botan_mp_to_hex+ :: BotanMP -- ^ __mp__+ -> Ptr CChar -- ^ __out__+ -> IO CInt++{- |+Convert the MPI to a string. Currently base == 10 and base == 16 are supported.++NOTE: base 16 encoding has an `0x` prefix, base 10 does not.++NOTE: Despite the size ptr, this appears to be returning null-terminated CStrings+-}+foreign import capi safe "botan/ffi.h botan_mp_to_str"+ botan_mp_to_str+ :: BotanMP -- ^ __mp__+ -> Word8 -- ^ __base__+ -> Ptr CChar -- ^ __out__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++-- | Set the MPI to zero+foreign import capi safe "botan/ffi.h botan_mp_clear"+ botan_mp_clear+ :: BotanMP -- ^ __mp__+ -> IO CInt++-- | Set the MPI value from an int+foreign import capi safe "botan/ffi.h botan_mp_set_from_int"+ botan_mp_set_from_int+ :: BotanMP -- ^ __mp__+ -> CInt -- ^ __initial_value__+ -> IO CInt++-- | Set the MPI value from another MP object+foreign import capi safe "botan/ffi.h botan_mp_set_from_mp"+ botan_mp_set_from_mp+ :: BotanMP -- ^ __dest__+ -> BotanMP -- ^ __source__+ -> IO CInt++-- | Set the MPI value from a string+foreign import capi safe "botan/ffi.h botan_mp_set_from_str"+ botan_mp_set_from_str+ :: BotanMP -- ^ __dest__+ -> ConstPtr CChar -- ^ __str__+ -> IO CInt++{- |+Set the MPI value from a string with arbitrary radix.+For arbitrary being 10 or 16.+-}+foreign import capi safe "botan/ffi.h botan_mp_set_from_radix_str"+ botan_mp_set_from_radix_str+ :: BotanMP -- ^ __dest__+ -> ConstPtr CChar -- ^ __str__+ -> CSize -- ^ __radix__+ -> IO CInt++-- | Return the number of significant bits in the MPI+foreign import capi safe "botan/ffi.h botan_mp_num_bits"+ botan_mp_num_bits+ :: BotanMP -- ^ __n__+ -> Ptr CSize -- ^ __bits__+ -> IO CInt++-- | Return the number of significant bytes in the MPI+foreign import capi safe "botan/ffi.h botan_mp_num_bytes"+ botan_mp_num_bytes+ :: BotanMP -- ^ __n__+ -> Ptr CSize -- ^ __bytes__+ -> IO CInt++-- | Convert the MPI to a big-endian binary string. Writes botan_mp_num_bytes to vec+foreign import capi safe "botan/ffi.h botan_mp_to_bin"+ botan_mp_to_bin+ :: BotanMP -- ^ __mp__+ -> Ptr Word8 -- ^ __vec[]__+ -> IO CInt++-- | Set an MP to the big-endian binary value+foreign import capi safe "botan/ffi.h botan_mp_from_bin"+ botan_mp_from_bin+ :: BotanMP -- ^ __mp__+ -> ConstPtr Word8 -- ^ __vec[]__+ -> CSize -- ^ __vec_len__+ -> IO CInt++-- | Convert the MPI to a uint32_t, if possible. Fails if MPI is negative or too large.+foreign import capi safe "botan/ffi.h botan_mp_to_uint32"+ botan_mp_to_uint32+ :: BotanMP -- ^ __mp__+ -> Ptr Word32 -- ^ __val__+ -> IO CInt++{- |+This function should have been named mp_is_non_negative. Returns 1+iff mp is greater than *or equal to* zero. Use botan_mp_is_negative+to detect negative numbers, botan_mp_is_zero to check for zero.+-}+foreign import capi safe "botan/ffi.h botan_mp_is_positive"+ botan_mp_is_positive+ :: BotanMP -- ^ __mp__+ -> IO CInt++-- | Return 1 iff mp is less than 0+foreign import capi safe "botan/ffi.h botan_mp_is_negative"+ botan_mp_is_negative+ :: BotanMP -- ^ __mp__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_flip_sign"+ botan_mp_flip_sign+ :: BotanMP -- ^ __mp__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_is_zero"+ botan_mp_is_zero+ :: BotanMP -- ^ __mp__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_add_u32"+ botan_mp_add_u32+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __x__+ -> Word32 -- ^ __y__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_sub_u32"+ botan_mp_sub_u32+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __x__+ -> Word32 -- ^ __y__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_add"+ botan_mp_add+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_sub"+ botan_mp_sub+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_mul"+ botan_mp_mul+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_div"+ botan_mp_div+ :: BotanMP -- ^ __quotient__+ -> BotanMP -- ^ __remainder__+ -> BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_mod_mul"+ botan_mp_mod_mul+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> BotanMP -- ^ __mod__+ -> IO CInt++{- |+Returns 0 if x != y+Returns 1 if x == y+Returns negative number on error+-}+foreign import capi safe "botan/ffi.h botan_mp_equal"+ botan_mp_equal+ :: BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++{- |+Sets *result to comparison result:+-1 if x < y, 0 if x == y, 1 if x > y+Returns negative number on error or zero on success+-}+foreign import capi safe "botan/ffi.h botan_mp_cmp"+ botan_mp_cmp+ :: Ptr CInt -- ^ __result__+ -> BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++-- | Swap two botan_mp_t+foreign import capi safe "botan/ffi.h botan_mp_swap"+ botan_mp_swap+ :: BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++-- | Return (base^exponent) % modulus +foreign import capi safe "botan/ffi.h botan_mp_powmod"+ botan_mp_powmod+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __base__+ -> BotanMP -- ^ __exponent__+ -> BotanMP -- ^ __modulus__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_lshift"+ botan_mp_lshift+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __n__+ -> CSize -- ^ __shift__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_rshift"+ botan_mp_rshift+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __n__+ -> CSize -- ^ __shift__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_mod_inverse"+ botan_mp_mod_inverse+ :: BotanMP -- ^ __result__+ -> BotanMP -- ^ __n__+ -> BotanMP -- ^ __modulus__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_rand_bits"+ botan_mp_rand_bits+ :: BotanMP -- ^ __rand_out__+ -> BotanRNG -- ^ __rng__+ -> CSize -- ^ __bits__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_rand_range"+ botan_mp_rand_range+ :: BotanMP -- ^ __rand_out__+ -> BotanRNG -- ^ __rng__+ -> BotanMP -- ^ __lower_bound__+ -> BotanMP -- ^ __upper_bound__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_mp_gcd"+ botan_mp_gcd+ :: BotanMP -- ^ __out__+ -> BotanMP -- ^ __x__+ -> BotanMP -- ^ __y__+ -> IO CInt++{- |+Returns 0 if n is not prime+Returns 1 if n is prime+Returns negative number on error+-}+foreign import capi safe "botan/ffi.h botan_mp_is_prime"+ botan_mp_is_prime+ :: BotanMP -- ^ __n__+ -> BotanRNG -- ^ __rng__+ -> CSize -- ^ __test_prob__+ -> IO CInt++{- |+Returns 0 if specified bit of n is not set+Returns 1 if specified bit of n is set+Returns negative number on error+-}+foreign import capi safe "botan/ffi.h botan_mp_get_bit"+ botan_mp_get_bit+ :: BotanMP -- ^ __n__+ -> CSize -- ^ __bit__+ -> IO CInt++-- | Set the specified bit+foreign import capi safe "botan/ffi.h botan_mp_set_bit"+ botan_mp_set_bit+ :: BotanMP -- ^ __n__+ -> CSize -- ^ __bit__+ -> IO CInt++-- | Clear the specified bit+foreign import capi safe "botan/ffi.h botan_mp_clear_bit"+ botan_mp_clear_bit+ :: BotanMP -- ^ __n__+ -> CSize -- ^ __bit__+ -> IO CInt
+ src/Botan/Bindings/Prelude.hs view
@@ -0,0 +1,66 @@+{-# LANGUAGE CApiFFI+ , CPP+ #-}++module Botan.Bindings.Prelude+( module Prelude+-- , module Data.ByteString+, module Data.String+, module Data.Word+, module System.IO+, module Foreign.C.String+, module Foreign.C.Types+, module Foreign.ForeignPtr+, module Foreign.Marshal.Alloc+, module Foreign.Marshal.Array+, module Foreign.Ptr+, module Foreign.Storable+, ConstPtr(..)+) where++import Prelude++-- import Data.ByteString (ByteString)+import Data.String (IsString(..))+import Data.Word++import System.IO++import Foreign.C.String+import Foreign.C.Types+import Foreign.ForeignPtr+import Foreign.Marshal.Alloc+import Foreign.Marshal.Array+import Foreign.Ptr+import Foreign.Storable+++#if MIN_VERSION_base (4,18,0)+import Foreign.C.ConstPtr+#else+import Data.Data+import Data.Kind+#endif++#if !(MIN_VERSION_base (4,18,0))++-- NOTE: Taken from Foreign.C.ConstPtr, more or less+-- NOTE: Raises a warning on older base / compilers if the shim+-- is a `newtype` instead of a `type`, because the special+-- logic for const pointers didn't exist yet+-- SEE: https://gitlab.haskell.org/ghc/ghc/-/issues/22043+-- AFFECTS:+-- botan_error_description+-- botan_error_last_exception_message+-- botan_x509_cert_validation_status+-- botan_version_string+type ConstPtr :: Type -> Type+type role ConstPtr phantom+newtype ConstPtr a = ConstPtr { unConstPtr :: Ptr a }+ deriving stock (Data)+ deriving newtype (Eq, Ord, Storable)++instance Show (ConstPtr a) where+ showsPrec d (ConstPtr p) = showParen (d > 10) $ showString "ConstPtr " . showsPrec 11 p++#endif
+ src/Botan/Bindings/PubKey.hsc view
@@ -0,0 +1,512 @@+{-|+Module : Botan.Bindings.PubKey+Description : Public key cryptography+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++Public key cryptography is a collection of techniques allowing+for encryption, signatures, and key agreement.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.RNG+import Botan.Bindings.View++#include <botan/ffi.h>++-- | Opaque PrivKey struct+data {-# CTYPE "botan/ffi.h" "struct botan_privkey_struct" #-} BotanPrivKeyStruct++-- | Botan PrivKey object+newtype {-# CTYPE "botan/ffi.h" "botan_privkey_t" #-} BotanPrivKey+ = MkBotanPrivKey { runBotanPrivKey :: Ptr BotanPrivKeyStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Frees all resources of the PrivKey object+foreign import capi safe "botan/ffi.h &botan_privkey_destroy"+ botan_privkey_destroy+ :: FinalizerPtr BotanPrivKeyStruct++pattern BOTAN_PK_RSA+ , BOTAN_PK_SM2+ , BOTAN_PK_ELGAMAL+ , BOTAN_PK_DSA+ , BOTAN_PK_ECDSA+ , BOTAN_PK_ECKCDSA+ , BOTAN_PK_ECGDSA+ , BOTAN_PK_GOST_34_10+ , BOTAN_PK_ED25519+ , BOTAN_PK_XMSS+ , BOTAN_PK_DH+ , BOTAN_PK_ECDH+ , BOTAN_PK_CURVE25519+ , BOTAN_PK_DILITHIUM+ , BOTAN_PK_KYBER+ -- , BOTAN_PK_SPHINCSPLUS+ , BOTAN_PK_MCELIECE+ :: (Eq a, IsString a) => a++pattern BOTAN_PK_RSA = "RSA"+pattern BOTAN_PK_SM2 = "SM2"+pattern BOTAN_PK_ELGAMAL = "ElGamal"+pattern BOTAN_PK_DSA = "DSA"+pattern BOTAN_PK_ECDSA = "ECDSA"+pattern BOTAN_PK_ECKCDSA = "ECKCDSA"+pattern BOTAN_PK_ECGDSA = "ECGDSA"+pattern BOTAN_PK_GOST_34_10 = "GOST-34.10"+pattern BOTAN_PK_ED25519 = "Ed25519"+pattern BOTAN_PK_XMSS = "XMSS"+pattern BOTAN_PK_DH = "DH"+pattern BOTAN_PK_ECDH = "ECDH"+pattern BOTAN_PK_CURVE25519 = "Curve25519"+pattern BOTAN_PK_DILITHIUM = "Dilithium"+pattern BOTAN_PK_KYBER = "Kyber"+-- pattern BOTAN_PK_SPHINCSPLUS = "SPHINCS+"+pattern BOTAN_PK_MCELIECE = "McEliece"++pattern BOTAN_XMSS_SHA2_10_256+ , BOTAN_XMSS_SHA2_16_256+ , BOTAN_XMSS_SHA2_20_256+ , BOTAN_XMSS_SHA2_10_512+ , BOTAN_XMSS_SHA2_16_512+ , BOTAN_XMSS_SHA2_20_512+ , BOTAN_XMSS_SHAKE_10_256+ , BOTAN_XMSS_SHAKE_16_256+ , BOTAN_XMSS_SHAKE_20_256+ , BOTAN_XMSS_SHAKE_10_512+ , BOTAN_XMSS_SHAKE_16_512+ , BOTAN_XMSS_SHAKE_20_512+ :: (Eq a, IsString a) => a++pattern BOTAN_XMSS_SHA2_10_256 = "XMSS-SHA2_10_256"+pattern BOTAN_XMSS_SHA2_16_256 = "XMSS-SHA2_16_256"+pattern BOTAN_XMSS_SHA2_20_256 = "XMSS-SHA2_20_256"+pattern BOTAN_XMSS_SHA2_10_512 = "XMSS-SHA2_10_512"+pattern BOTAN_XMSS_SHA2_16_512 = "XMSS-SHA2_16_512"+pattern BOTAN_XMSS_SHA2_20_512 = "XMSS-SHA2_20_512"+pattern BOTAN_XMSS_SHAKE_10_256 = "XMSS-SHAKE_10_256"+pattern BOTAN_XMSS_SHAKE_16_256 = "XMSS-SHAKE_16_256"+pattern BOTAN_XMSS_SHAKE_20_256 = "XMSS-SHAKE_20_256"+pattern BOTAN_XMSS_SHAKE_10_512 = "XMSS-SHAKE_10_512"+pattern BOTAN_XMSS_SHAKE_16_512 = "XMSS-SHAKE_16_512"+pattern BOTAN_XMSS_SHAKE_20_512 = "XMSS-SHAKE_20_512"++pattern BOTAN_ECGROUP_SECP_160_K1+ , BOTAN_ECGROUP_SECP_160_R1+ , BOTAN_ECGROUP_SECP_160_R2+ , BOTAN_ECGROUP_SECP_192_K1+ , BOTAN_ECGROUP_SECP_192_R1+ , BOTAN_ECGROUP_SECP_224_K1+ , BOTAN_ECGROUP_SECP_224_R1+ , BOTAN_ECGROUP_SECP_256_K1+ , BOTAN_ECGROUP_SECP_256_R1+ , BOTAN_ECGROUP_SECP_384_R1+ , BOTAN_ECGROUP_SECP_521_R1+ , BOTAN_ECGROUP_BRAINPOOL_160_R1+ , BOTAN_ECGROUP_BRAINPOOL_192_R1+ , BOTAN_ECGROUP_BRAINPOOL_224_R1+ , BOTAN_ECGROUP_BRAINPOOL_256_R1+ , BOTAN_ECGROUP_BRAINPOOL_320_R1+ , BOTAN_ECGROUP_BRAINPOOL_384_R1+ , BOTAN_ECGROUP_BRAINPOOL_512_R1+ , BOTAN_ECGROUP_X962_P192_V2+ , BOTAN_ECGROUP_X962_P192_V3+ , BOTAN_ECGROUP_X962_P239_V1+ , BOTAN_ECGROUP_X962_P239_V2+ , BOTAN_ECGROUP_X962_P239_V3+ , BOTAN_ECGROUP_GOST_256A+ , BOTAN_ECGROUP_GOST_512A+ , BOTAN_ECGROUP_FRP_256_V1+ , BOTAN_ECGROUP_SM2_P256_V1+ :: (Eq a, IsString a) => a++pattern BOTAN_ECGROUP_SECP_160_K1 = "secp160k1"+pattern BOTAN_ECGROUP_SECP_160_R1 = "secp160r1"+pattern BOTAN_ECGROUP_SECP_160_R2 = "secp160r2"+pattern BOTAN_ECGROUP_SECP_192_K1 = "secp192k1"+pattern BOTAN_ECGROUP_SECP_192_R1 = "secp192r1"+pattern BOTAN_ECGROUP_SECP_224_K1 = "secp224k1"+pattern BOTAN_ECGROUP_SECP_224_R1 = "secp224r1"+pattern BOTAN_ECGROUP_SECP_256_K1 = "secp256k1"+pattern BOTAN_ECGROUP_SECP_256_R1 = "secp256r1"+pattern BOTAN_ECGROUP_SECP_384_R1 = "secp384r1"+pattern BOTAN_ECGROUP_SECP_521_R1 = "secp521r1"+pattern BOTAN_ECGROUP_BRAINPOOL_160_R1 = "brainpool160r1"+pattern BOTAN_ECGROUP_BRAINPOOL_192_R1 = "brainpool192r1"+pattern BOTAN_ECGROUP_BRAINPOOL_224_R1 = "brainpool224r1"+pattern BOTAN_ECGROUP_BRAINPOOL_256_R1 = "brainpool256r1"+pattern BOTAN_ECGROUP_BRAINPOOL_320_R1 = "brainpool320r1"+pattern BOTAN_ECGROUP_BRAINPOOL_384_R1 = "brainpool384r1"+pattern BOTAN_ECGROUP_BRAINPOOL_512_R1 = "brainpool512r1"+pattern BOTAN_ECGROUP_X962_P192_V2 = "x962_p192v2"+pattern BOTAN_ECGROUP_X962_P192_V3 = "x962_p192v3"+pattern BOTAN_ECGROUP_X962_P239_V1 = "x962_p239v1"+pattern BOTAN_ECGROUP_X962_P239_V2 = "x962_p239v2"+pattern BOTAN_ECGROUP_X962_P239_V3 = "x962_p239v3"+pattern BOTAN_ECGROUP_GOST_256A = "gost_256A"+pattern BOTAN_ECGROUP_GOST_512A = "gost_512A"+pattern BOTAN_ECGROUP_FRP_256_V1 = "frp256v1"+pattern BOTAN_ECGROUP_SM2_P256_V1 = "sm2p256v1"++pattern BOTAN_DLGROUP_FFDHE_IETF_2048+ , BOTAN_DLGROUP_FFDHE_IETF_3072+ , BOTAN_DLGROUP_FFDHE_IETF_4096+ , BOTAN_DLGROUP_FFDHE_IETF_6144+ , BOTAN_DLGROUP_FFDHE_IETF_8192+ , BOTAN_DLGROUP_MODP_IETF_1024+ , BOTAN_DLGROUP_MODP_IETF_1536+ , BOTAN_DLGROUP_MODP_IETF_2048+ , BOTAN_DLGROUP_MODP_IETF_3072+ , BOTAN_DLGROUP_MODP_IETF_4096+ , BOTAN_DLGROUP_MODP_IETF_6144+ , BOTAN_DLGROUP_MODP_IETF_8192+ , BOTAN_DLGROUP_MODP_SRP_1024+ , BOTAN_DLGROUP_MODP_SRP_1536+ , BOTAN_DLGROUP_MODP_SRP_2048+ , BOTAN_DLGROUP_MODP_SRP_3072+ , BOTAN_DLGROUP_MODP_SRP_4096+ , BOTAN_DLGROUP_MODP_SRP_6144+ , BOTAN_DLGROUP_MODP_SRP_8192+ , BOTAN_DLGROUP_DSA_JCE_1024+ , BOTAN_DLGROUP_DSA_BOTAN_2048+ , BOTAN_DLGROUP_DSA_BOTAN_3072+ :: (Eq a, IsString a) => a++pattern BOTAN_DLGROUP_FFDHE_IETF_2048 = "ffdhe/ietf/2048"+pattern BOTAN_DLGROUP_FFDHE_IETF_3072 = "ffdhe/ietf/3072"+pattern BOTAN_DLGROUP_FFDHE_IETF_4096 = "ffdhe/ietf/4096"+pattern BOTAN_DLGROUP_FFDHE_IETF_6144 = "ffdhe/ietf/6144"+pattern BOTAN_DLGROUP_FFDHE_IETF_8192 = "ffdhe/ietf/8192"+pattern BOTAN_DLGROUP_MODP_IETF_1024 = "modp/ietf/1024"+pattern BOTAN_DLGROUP_MODP_IETF_1536 = "modp/ietf/1536"+pattern BOTAN_DLGROUP_MODP_IETF_2048 = "modp/ietf/2048"+pattern BOTAN_DLGROUP_MODP_IETF_3072 = "modp/ietf/3072"+pattern BOTAN_DLGROUP_MODP_IETF_4096 = "modp/ietf/4096"+pattern BOTAN_DLGROUP_MODP_IETF_6144 = "modp/ietf/6144"+pattern BOTAN_DLGROUP_MODP_IETF_8192 = "modp/ietf/8192"+pattern BOTAN_DLGROUP_MODP_SRP_1024 = "modp/srp/1024"+pattern BOTAN_DLGROUP_MODP_SRP_1536 = "modp/srp/1536"+pattern BOTAN_DLGROUP_MODP_SRP_2048 = "modp/srp/2048"+pattern BOTAN_DLGROUP_MODP_SRP_3072 = "modp/srp/3072"+pattern BOTAN_DLGROUP_MODP_SRP_4096 = "modp/srp/4096"+pattern BOTAN_DLGROUP_MODP_SRP_6144 = "modp/srp/6144"+pattern BOTAN_DLGROUP_MODP_SRP_8192 = "modp/srp/8192"+pattern BOTAN_DLGROUP_DSA_JCE_1024 = "dsa/jce/1024"+pattern BOTAN_DLGROUP_DSA_BOTAN_2048 = "dsa/botan/2048"+pattern BOTAN_DLGROUP_DSA_BOTAN_3072 = "dsa/botan/3072"++pattern BOTAN_EME_RAW+ , BOTAN_EME_PKCS1_v1_5+ , BOTAN_EME_OAEP+ :: (Eq a, IsString a) => a++pattern BOTAN_EME_RAW = "Raw"+pattern BOTAN_EME_PKCS1_v1_5 = "PKCS1v15"+pattern BOTAN_EME_OAEP = "OAEP"++pattern BOTAN_MGF_MGF1+ :: (Eq a, IsString a) => a++pattern BOTAN_MGF_MGF1 = "MGF1"++-- | Create a new private key+foreign import capi safe "botan/ffi.h botan_privkey_create"+ botan_privkey_create+ :: Ptr BotanPrivKey -- ^ __key__: the new object will be placed here+ -> ConstPtr CChar -- ^ __algo_name__: something like "RSA" or "ECDSA"+ -> ConstPtr CChar -- ^ __algo_params__: is specific to the algorithm. For RSA, specifies+ -- the modulus bit length. For ECC is the name of the curve.+ -> BotanRNG -- ^ __rng__: a random number generator+ -> IO CInt++pattern BOTAN_CHECK_KEY_NORMAL_TESTS+ , BOTAN_CHECK_KEY_EXPENSIVE_TESTS+ :: (Eq a, Num a) => a+pattern BOTAN_CHECK_KEY_NORMAL_TESTS = 0+pattern BOTAN_CHECK_KEY_EXPENSIVE_TESTS = #const BOTAN_CHECK_KEY_EXPENSIVE_TESTS++-- | Check the validity of a private key+foreign import capi safe "botan/ffi.h botan_privkey_check_key"+ botan_privkey_check_key+ :: BotanPrivKey -- ^ __key__+ -> BotanRNG -- ^ __rng__+ -> Word32 -- ^ __flags__+ -> IO CInt++{- |+Input currently assumed to be PKCS #8 structure;+Set password to NULL to indicate no encryption expected+Starting in 2.8.0, the rng parameter is unused and may be set to null+-}+foreign import capi safe "botan/ffi.h botan_privkey_load"+ botan_privkey_load+ :: Ptr BotanPrivKey -- ^ __key__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr Word8 -- ^ __bits[]__+ -> CSize -- ^ __len__+ -> ConstPtr CChar -- ^ __password__+ -> IO CInt++pattern BOTAN_PRIVKEY_EXPORT_FLAG_DER+ , BOTAN_PRIVKEY_EXPORT_FLAG_PEM+ :: (Eq a, Num a) => a+pattern BOTAN_PRIVKEY_EXPORT_FLAG_DER = #const BOTAN_PRIVKEY_EXPORT_FLAG_DER+pattern BOTAN_PRIVKEY_EXPORT_FLAG_PEM = #const BOTAN_PRIVKEY_EXPORT_FLAG_PEM++{- |+On input *out_len is number of bytes in out[]+On output *out_len is number of bytes written (or required)+If out is not big enough no output is written, *out_len is set and 1 is returned+Returns 0 on success and sets+If some other error occurs a negative integer is returned.+-}+foreign import capi safe "botan/ffi.h botan_privkey_export"+ botan_privkey_export+ :: BotanPrivKey -- ^ __key__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> Word32 -- ^ __flags__+ -> IO CInt++-- | View the private key's DER encoding+foreign import capi safe "botan/ffi.h botan_privkey_view_der"+ botan_privkey_view_der+ :: BotanPrivKey -- ^ __key__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewBinCallback ctx) -- ^ __view__+ -> IO CInt++-- | View the private key's PEM encoding+foreign import capi safe "botan/ffi.h botan_privkey_view_pem"+ botan_privkey_view_pem+ :: BotanPrivKey -- ^ __key__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewStrCallback ctx) -- ^ __view__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_algo_name"+ botan_privkey_algo_name+ :: BotanPrivKey -- ^ __key__+ -> Ptr CChar -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++{- |+Export a private key, running PBKDF for specified amount of time++Note: starting in 3.0, the output iterations count is not provided+-}+foreign import capi safe "botan/ffi.h botan_privkey_export_encrypted_pbkdf_msec"+ botan_privkey_export_encrypted_pbkdf_msec+ :: BotanPrivKey -- ^ __key__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr CChar -- ^ __passphrase__+ -> Word32 -- ^ __pbkdf_msec_runtime__+ -> Ptr CSize -- ^ __pbkdf_iterations_out__+ -> ConstPtr CChar -- ^ __cipher_algo__+ -> ConstPtr CChar -- ^ __pbkdf_algo__+ -> Word32 -- ^ __flags__+ -> IO CInt++-- | Export a private key using the specified number of iterations.+foreign import capi safe "botan/ffi.h botan_privkey_export_encrypted_pbkdf_iter"+ botan_privkey_export_encrypted_pbkdf_iter+ :: BotanPrivKey -- ^ __key__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr CChar -- ^ __passphrase__+ -> CSize -- ^ __pbkdf_iterations__+ -> ConstPtr CChar -- ^ __cipher_algo__+ -> ConstPtr CChar -- ^ __pbkdf_algo__+ -> Word32 -- ^ __flags__+ -> IO CInt++{- |+View the encryption of a private key (binary DER encoding)++Set cipher_algo, pbkdf_algo to NULL to use defaults+Set pbkdf_iterations to 0 to use defaults+-}+foreign import capi safe "botan/ffi.h botan_privkey_view_encrypted_der"+ botan_privkey_view_encrypted_der+ :: BotanPrivKey -- ^ __key__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr CChar -- ^ __passphrase__+ -> ConstPtr CChar -- ^ __cipher_algo__+ -> ConstPtr CChar -- ^ __pbkdf_algo__+ -> CSize -- ^ __pbkdf_iterations__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewBinCallback ctx) -- ^ __view__+ -> IO CInt++{- |+View the encryption of a private key (binary DER encoding)++Set cipher_algo, pbkdf_algo to NULL to use defaults+-}+foreign import capi safe "botan/ffi.h botan_privkey_view_encrypted_der_timed"+ botan_privkey_view_encrypted_der_timed+ :: BotanPrivKey -- ^ __key__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr CChar -- ^ __passphrase__+ -> ConstPtr CChar -- ^ __cipher_algo__+ -> ConstPtr CChar -- ^ __pbkdf_algo__+ -> CSize -- ^ __pbkdf_runtime_msec__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewBinCallback ctx) -- ^ __view__+ -> IO CInt++{- |+View the encryption of a private key (PEM encoding)++Set cipher_algo, pbkdf_algo to NULL to use defaults+Set pbkdf_iterations to 0 to use defaults+-}+foreign import capi safe "botan/ffi.h botan_privkey_view_encrypted_pem"+ botan_privkey_view_encrypted_pem+ :: BotanPrivKey -- ^ __key__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr CChar -- ^ __passphrase__+ -> ConstPtr CChar -- ^ __cipher_algo__+ -> ConstPtr CChar -- ^ __pbkdf_algo__+ -> CSize -- ^ __pbkdf_iterations__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewStrCallback ctx) -- ^ __view__+ -> IO CInt++{- |+View the encryption of a private key (PEM encoding)++Set cipher_algo, pbkdf_algo to NULL to use defaults+-}+foreign import capi safe "botan/ffi.h botan_privkey_view_encrypted_pem_timed"+ botan_privkey_view_encrypted_pem_timed+ :: BotanPrivKey -- ^ __key__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr CChar -- ^ __passphrase__+ -> ConstPtr CChar -- ^ __cipher_algo__+ -> ConstPtr CChar -- ^ __pbkdf_algo__+ -> CSize -- ^ __pbkdf_runtime_msec__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewStrCallback ctx) -- ^ __view__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_get_field"+ botan_privkey_get_field+ :: BotanMP -- ^ __output__+ -> BotanPrivKey -- ^ __key__+ -> ConstPtr CChar -- ^ __field_name__+ -> IO CInt+++-- | Opaque PubKey struct+data {-# CTYPE "botan/ffi.h" "struct botan_pubkey_struct" #-} BotanPubKeyStruct++-- | Botan PubKey object+newtype {-# CTYPE "botan/ffi.h" "botan_pubkey_t" #-} BotanPubKey+ = MkBotanPubKey { runBotanPubKey :: Ptr BotanPubKeyStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Frees all resources of the PubKey object+foreign import capi safe "botan/ffi.h &botan_pubkey_destroy"+ botan_pubkey_destroy+ :: FinalizerPtr BotanPubKeyStruct++foreign import capi safe "botan/ffi.h botan_privkey_export_pubkey"+ botan_privkey_export_pubkey+ :: Ptr BotanPubKey -- ^ __out__+ -> BotanPrivKey -- ^ __in__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_load"+ botan_pubkey_load+ :: Ptr BotanPubKey -- ^ __key__+ -> ConstPtr Word8 -- ^ __bits[]__+ -> CSize -- ^ __len__+ -> IO CInt++pattern BOTAN_PUBKEY_EXPORT_FLAG_DER -- ^ __BOTAN_PRIVKEY_EXPORT_FLAG_DER__ in disguise+ , BOTAN_PUBKEY_EXPORT_FLAG_PEM -- ^ __BOTAN_PRIVKEY_EXPORT_FLAG_PEM__ in disguise+ :: (Eq a, Num a) => a+pattern BOTAN_PUBKEY_EXPORT_FLAG_DER = BOTAN_PRIVKEY_EXPORT_FLAG_DER+pattern BOTAN_PUBKEY_EXPORT_FLAG_PEM = BOTAN_PRIVKEY_EXPORT_FLAG_PEM++foreign import capi safe "botan/ffi.h botan_pubkey_export"+ botan_pubkey_export+ :: BotanPubKey -- ^ __key__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> Word32 -- ^ __flags__+ -> IO CInt++-- | View the public key's DER encoding+foreign import capi safe "botan/ffi.h botan_pubkey_view_der"+ botan_pubkey_view_der+ :: BotanPubKey -- ^ __key__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewBinCallback ctx) -- ^ __view__+ -> IO CInt+ + -- | View the public key's PEM encoding+foreign import capi safe "botan/ffi.h botan_pubkey_view_pem"+ botan_pubkey_view_pem+ :: BotanPubKey -- ^ __key__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewStrCallback ctx) -- ^ __view__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_algo_name"+ botan_pubkey_algo_name+ :: BotanPubKey -- ^ __key__+ -> Ptr CChar -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++-- | Returns 0 if key is valid, negative if invalid key or some other error+foreign import capi safe "botan/ffi.h botan_pubkey_check_key"+ botan_pubkey_check_key+ :: BotanPubKey -- ^ __key__+ -> BotanRNG -- ^ __rng__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_estimated_strength"+ botan_pubkey_estimated_strength+ :: BotanPubKey -- ^ __key__+ -> Ptr CSize -- ^ __estimate__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_fingerprint"+ botan_pubkey_fingerprint+ :: BotanPubKey -- ^ __key__+ -> ConstPtr CChar -- ^ __hash__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++-- | Get arbitrary named fields from public or private keys+foreign import capi safe "botan/ffi.h botan_pubkey_get_field"+ botan_pubkey_get_field+ :: BotanMP -- ^ __output__+ -> BotanPubKey -- ^ __key__+ -> ConstPtr CChar -- ^ __field_name__+ -> IO CInt++-- | View the uncompressed public point associated with the key+foreign import capi safe "botan/ffi.h botan_pubkey_view_ec_public_point"+ botan_pubkey_view_ec_public_point+ :: BotanPubKey -- ^ __key__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewBinCallback ctx) -- ^ __view__+ -> IO CInt
+ src/Botan/Bindings/PubKey/DH.hs view
@@ -0,0 +1,35 @@+{-|+Module : Botan.Bindings.DSA+Description : Algorithm specific key operations: Diffie Hellman+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.DH where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++-- | Loads Diffie Hellman private key+foreign import capi safe "botan/ffi.h botan_privkey_load_dh"+ botan_privkey_load_dh+ :: Ptr BotanPrivKey -- ^ __key__: variable populated with key material+ -> BotanMP -- ^ __p__: prime order of a Z_p group+ -> BotanMP -- ^ __g__: group generator+ -> BotanMP -- ^ __x__: private key+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Loads Diffie Hellman public key+foreign import capi safe "botan/ffi.h botan_pubkey_load_dh"+ botan_pubkey_load_dh+ :: Ptr BotanPubKey -- ^ __key__: variable populated with key material+ -> BotanMP -- ^ __p__: prime order of a Z_p group+ -> BotanMP -- ^ __g__: group generator+ -> BotanMP -- ^ __y__: public key+ -> IO CInt -- ^ 0 on success, a negative value on failure
+ src/Botan/Bindings/PubKey/DSA.hs view
@@ -0,0 +1,53 @@+{-|+Module : Botan.Bindings.DSA+Description : Algorithm specific key operations: DSA+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.DSA where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.RNG++{- |+Generates DSA key pair. Gives to a caller control over key length+and order of a subgroup 'q'.+-}+foreign import capi safe "botan/ffi.h botan_privkey_create_dsa"+ botan_privkey_create_dsa+ :: Ptr BotanPrivKey -- ^ __key__: handler to the resulting key+ -> BotanRNG -- ^ __rng__: initialized PRNG+ -> CSize -- ^ __pbits__: length of the key in bits. Must be between in range (1024, 3072)+ -- and multiple of 64. Bit size of the prime 'p'+ -> CSize -- ^ __qbits__: qbits order of the subgroup. Must be in range (160, 256) and multiple+ -- of 8+ -> IO CInt -- ^ BOTAN_FFI_SUCCESS Success, `key' initialized with DSA key+ -- BOTAN_FFI_ERROR_NULL_POINTER either `key' or `rng' is NULL+ -- BOTAN_FFI_ERROR_BAD_PARAMETER unexpected value for either `pbits' or `qbits'+ -- BOTAN_FFI_ERROR_NOT_IMPLEMENTED functionality not implemented++foreign import capi safe "botan/ffi.h botan_privkey_load_dsa"+ botan_privkey_load_dsa+ :: Ptr BotanPrivKey -- ^ __key__+ -> BotanMP -- ^ __p__+ -> BotanMP -- ^ __q__+ -> BotanMP -- ^ __g__+ -> BotanMP -- ^ __x__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_load_dsa"+ botan_pubkey_load_dsa+ :: Ptr BotanPubKey -- ^ __key__+ -> BotanMP -- ^ __p__+ -> BotanMP -- ^ __q__+ -> BotanMP -- ^ __g__+ -> BotanMP -- ^ __y__+ -> IO CInt
+ src/Botan/Bindings/PubKey/Decrypt.hsc view
@@ -0,0 +1,59 @@+{-|+Module : Botan.Bindings.Decrypt+Description : Public Key Decryption+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.Decrypt where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++#include <botan/ffi.h>++-- | Opaque decrypt struct+data {-# CTYPE "botan/ffi.h" "struct botan_pk_op_decrypt_struct" #-} BotanPKOpDecryptStruct++-- | Botan decrypt object+newtype {-# CTYPE "botan/ffi.h" "botan_pk_op_decrypt_t" #-} BotanPKOpDecrypt+ = MkBotanPKOpDecrypt { runBotanPKOpDecrypt :: Ptr BotanPKOpDecryptStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a decrypt object+foreign import capi safe "botan/ffi.h &botan_pk_op_decrypt_destroy"+ botan_pk_op_decrypt_destroy+ :: FinalizerPtr BotanPKOpDecryptStruct++pattern BOTAN_PUBKEY_DECRYPT_FLAGS_NONE -- ^ Not actual flag+ :: (Eq a, Num a) => a+pattern BOTAN_PUBKEY_DECRYPT_FLAGS_NONE = 0++foreign import capi safe "botan/ffi.h botan_pk_op_decrypt_create"+ botan_pk_op_decrypt_create+ :: Ptr BotanPKOpDecrypt -- ^ __op__+ -> BotanPrivKey -- ^ __key__+ -> Ptr CChar -- ^ __padding__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_decrypt_output_length"+ botan_pk_op_decrypt_output_length+ :: BotanPKOpDecrypt -- ^ __op__+ -> CSize -- ^ __ctext_len__+ -> Ptr CSize -- ^ __ptext_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_decrypt"+ botan_pk_op_decrypt+ :: BotanPKOpDecrypt -- ^ __op__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> ConstPtr Word8 -- ^ __ciphertext__+ -> CSize -- ^ __ciphertext_len__+ -> IO CInt
+ src/Botan/Bindings/PubKey/ECDH.hs view
@@ -0,0 +1,32 @@+{-|+Module : Botan.Bindings.ECDH+Description : Algorithm specific key operations: ECDH+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.ECDH where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++foreign import capi safe "botan/ffi.h botan_pubkey_load_ecdh"+ botan_pubkey_load_ecdh+ :: Ptr BotanPubKey -- ^ __key__+ -> BotanMP -- ^ __public_x__+ -> BotanMP -- ^ __public_y__+ -> ConstPtr CChar -- ^ __curve_name__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_load_ecdh"+ botan_privkey_load_ecdh+ :: Ptr BotanPrivKey -- ^ __key__+ -> BotanMP -- ^ __scalar__+ -> ConstPtr CChar -- ^ __curve_name__+ -> IO CInt
+ src/Botan/Bindings/PubKey/ECDSA.hs view
@@ -0,0 +1,32 @@+{-|+Module : Botan.Bindings.ECDSA+Description : Algorithm specific key operations: ECDSA+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.ECDSA where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++foreign import capi safe "botan/ffi.h botan_privkey_load_ecdsa"+ botan_privkey_load_ecdsa+ :: Ptr BotanPrivKey -- ^ __key__+ -> BotanMP -- ^ __scalar__+ -> ConstPtr CChar -- ^ __curve_name__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_load_ecdsa"+ botan_pubkey_load_ecdsa+ :: Ptr BotanPubKey -- ^ __key__+ -> BotanMP -- ^ __public_x__+ -> BotanMP -- ^ __public_y__+ -> ConstPtr CChar -- ^ __curve_name__+ -> IO CInt
+ src/Botan/Bindings/PubKey/Ed25519.hs view
@@ -0,0 +1,40 @@+{-|+Module : Botan.Bindings.Ed25519+Description : Algorithm specific key operations: Ed25519+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.Ed25519 where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++foreign import capi safe "botan/ffi.h botan_privkey_load_ed25519"+ botan_privkey_load_ed25519+ :: Ptr BotanPrivKey -- ^ __key__+ -> ConstPtr Word8 -- ^ __privkey[32]__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_load_ed25519"+ botan_pubkey_load_ed25519+ :: Ptr BotanPubKey -- ^ __key__+ -> ConstPtr Word8 -- ^ __pubkey[32]__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_ed25519_get_privkey"+ botan_privkey_ed25519_get_privkey+ :: BotanPrivKey -- ^ __key__+ -> Ptr Word8 -- ^ __output[64]__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_ed25519_get_pubkey"+ botan_pubkey_ed25519_get_pubkey+ :: BotanPubKey -- ^ __key__+ -> Ptr Word8 -- ^ __pubkey[32]__+ -> IO CInt
+ src/Botan/Bindings/PubKey/ElGamal.hs view
@@ -0,0 +1,56 @@+{-|+Module : Botan.Bindings.PubKey.ElGamal+Description : Algorithm specific key operations: ElGamal+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.ElGamal where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.RNG++{- |+Generates ElGamal key pair. Caller has a control over key length+and order of a subgroup 'q'. Function is able to use two types of+primes:++ * if pbits-1 == qbits then safe primes are used for key generation++ * otherwise generation uses group of prime order+-}+foreign import capi safe "botan/ffi.h botan_privkey_create_elgamal"+ botan_privkey_create_elgamal+ :: Ptr BotanPrivKey -- ^ __key__: handler to the resulting key+ -> BotanRNG -- ^ __rng__: initialized PRNG+ -> CSize -- ^ __pbits__: length of the key in bits. Must be at least 1024+ -> CSize -- ^ __qbits__: order of the subgroup. Must be at least 160+ -> IO CInt -- ^ - BOTAN_FFI_SUCCESS Success, `key' initialized with DSA key+ -- - BOTAN_FFI_ERROR_NULL_POINTER either `key' or `rng' is NULL+ -- - BOTAN_FFI_ERROR_BAD_PARAMETER unexpected value for either `pbits' or `qbits'+ -- - BOTAN_FFI_ERROR_NOT_IMPLEMENTED functionality not implemented++-- | Loads ElGamal private key+foreign import capi safe "botan/ffi.h botan_pubkey_load_elgamal"+ botan_pubkey_load_elgamal+ :: Ptr BotanPubKey -- ^ __key__: variable populated with key material+ -> BotanMP -- ^ __p__: prime order of a Z_p group+ -> BotanMP -- ^ __g__: group generator+ -> BotanMP -- ^ __y__: private key+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Loads ElGamal public key+foreign import capi safe "botan/ffi.h botan_privkey_load_elgamal"+ botan_privkey_load_elgamal+ :: Ptr BotanPrivKey -- ^ __key__: variable populated with key material+ -> BotanMP -- ^ __p__: prime order of a Z_p group+ -> BotanMP -- ^ __g__: group generator+ -> BotanMP -- ^ __x__: public key+ -> IO CInt -- ^ 0 on success, a negative value on failure
+ src/Botan/Bindings/PubKey/Encrypt.hsc view
@@ -0,0 +1,61 @@+{-|+Module : Botan.Bindings.Encrypt+Description : Public Key Encryption+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.Encrypt where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.RNG++#include <botan/ffi.h>++-- | Opaque encrypt struct+data {-# CTYPE "botan/ffi.h" "struct botan_pk_op_encrypt_struct" #-} BotanPKOpEncryptStruct++-- | Botan encrypt object+newtype {-# CTYPE "botan/ffi.h" "botan_pk_op_encrypt_t" #-} BotanPKOpEncrypt+ = MkBotanPKOpEncrypt { runBotanPKOpEncrypt :: Ptr BotanPKOpEncryptStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a encrypt object+foreign import capi safe "botan/ffi.h &botan_pk_op_encrypt_destroy"+ botan_pk_op_encrypt_destroy+ :: FinalizerPtr BotanPKOpEncryptStruct++pattern BOTAN_PUBKEY_ENCRYPT_FLAGS_NONE -- ^ Not actual flag+ :: (Eq a, Num a) => a+pattern BOTAN_PUBKEY_ENCRYPT_FLAGS_NONE = 0++foreign import capi safe "botan/ffi.h botan_pk_op_encrypt_create"+ botan_pk_op_encrypt_create+ :: Ptr BotanPKOpEncrypt -- ^ __op__+ -> BotanPubKey -- ^ __key__+ -> ConstPtr CChar -- ^ __padding__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_encrypt_output_length"+ botan_pk_op_encrypt_output_length+ :: BotanPKOpEncrypt -- ^ __op__+ -> CSize -- ^ __ptext_len__+ -> Ptr CSize -- ^ __ctext_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_encrypt"+ botan_pk_op_encrypt+ :: BotanPKOpEncrypt -- ^ __op__+ -> BotanRNG -- ^ __rng__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> Ptr Word8 -- ^ __plaintext[]__+ -> CSize -- ^ __plaintext_len__+ -> IO CInt
+ src/Botan/Bindings/PubKey/KeyAgreement.hsc view
@@ -0,0 +1,77 @@+{-|+Module : Botan.Bindings.KeyAgreement+Description : Key Agreement+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.KeyAgreement where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.View++#include <botan/ffi.h>++-- NOTE: Asymmetry in naming of struct vs functions++-- | Opaque key agreement struct+data {-# CTYPE "botan/ffi.h" "struct botan_pk_op_ka_struct" #-} BotanPKOpKeyAgreementStruct++-- | Botan key agreement object+newtype {-# CTYPE "botan/ffi.h" "botan_pk_op_ka_t" #-} BotanPKOpKeyAgreement+ = MkBotanPKOpKeyAgreement { runBotanPKOpKeyAgreement :: Ptr BotanPKOpKeyAgreementStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a key agreement object+foreign import capi safe "botan/ffi.h &botan_pk_op_key_agreement_destroy"+ botan_pk_op_key_agreement_destroy+ :: FinalizerPtr BotanPKOpKeyAgreementStruct++pattern BOTAN_PUBKEY_KEY_AGREEMENT_FLAGS_NONE -- ^ Not actual flag+ :: (Eq a, Num a) => a+pattern BOTAN_PUBKEY_KEY_AGREEMENT_FLAGS_NONE = 0++foreign import capi safe "botan/ffi.h botan_pk_op_key_agreement_create"+ botan_pk_op_key_agreement_create+ :: Ptr BotanPKOpKeyAgreement -- ^ __op__+ -> BotanPrivKey -- ^ __key__+ -> ConstPtr CChar -- ^ __kdf__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_key_agreement_export_public"+ botan_pk_op_key_agreement_export_public+ :: BotanPrivKey -- ^ __key__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_key_agreement_view_public"+ botan_pk_op_key_agreement_view_public+ :: BotanPrivKey -- ^ __key__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewBinCallback ctx) -- ^ __view__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_key_agreement_size"+ botan_pk_op_key_agreement_size+ :: BotanPKOpKeyAgreement -- ^ __op__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_key_agreement"+ botan_pk_op_key_agreement+ :: BotanPKOpKeyAgreement -- ^ __op__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__,+ -> ConstPtr Word8 -- ^ __other_key[]__+ -> CSize -- ^ __other_key_len__+ -> ConstPtr Word8 -- ^ __salt[]__+ -> CSize -- ^ __salt_len__+ -> IO CInt
+ src/Botan/Bindings/PubKey/KeyEncapsulation.hs view
@@ -0,0 +1,102 @@+{-|+Module : Botan.Bindings.KeyEncapsulation+Description : Key Encapsulation+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.KeyEncapsulation where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.RNG++-- | Opaque KEM encrypt struct+data {-# CTYPE "botan/ffi.h" "struct botan_pk_op_kem_encrypt_struct" #-} BotanPKOpKEMEncryptStruct++-- | Botan KEM encrypt object+newtype {-# CTYPE "botan/ffi.h" "botan_pk_op_kem_encrypt_t" #-} BotanPKOpKEMEncrypt+ = MkBotanPKOpKEMEncrypt { runBotanPKOpKEMEncrypt :: Ptr BotanPKOpKEMEncryptStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a KEM encrypt object+foreign import capi safe "botan/ffi.h &botan_pk_op_kem_encrypt_destroy"+ botan_pk_op_kem_encrypt_destroy+ :: FinalizerPtr BotanPKOpKEMEncryptStruct++foreign import capi safe "botan/ffi.h botan_pk_op_kem_encrypt_create"+ botan_pk_op_kem_encrypt_create+ :: Ptr BotanPKOpKEMEncrypt -- ^ __op__+ -> BotanPubKey -- ^ __key__+ -> ConstPtr CChar -- ^ __kdf__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_kem_encrypt_shared_key_length"+ botan_pk_op_kem_encrypt_shared_key_length+ :: BotanPKOpKEMEncrypt -- ^ __op__+ -> CSize -- ^ __desired_shared_key_length__+ -> Ptr CSize -- ^ __output_shared_key_length__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_kem_encrypt_encapsulated_key_length"+ botan_pk_op_kem_encrypt_encapsulated_key_length+ :: BotanPKOpKEMEncrypt -- ^ __op__+ -> Ptr CSize -- ^ __output_encapsulated_key_length__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_kem_encrypt_create_shared_key"+ botan_pk_op_kem_encrypt_create_shared_key+ :: BotanPKOpKEMEncrypt -- ^ __op__+ -> BotanRNG -- ^ __rng__+ -> ConstPtr Word8 -- ^ __salt[]__+ -> CSize -- ^ __salt_len__+ -> CSize -- ^ __desired_shared_key_len__+ -> Ptr Word8 -- ^ __shared_key[]__+ -> Ptr CSize -- ^ __shared_key_len__+ -> Ptr Word8 -- ^ __encapsulated_key[]__+ -> Ptr CSize -- ^ __encapsulated_key_len__+ -> IO CInt++-- | Opaque KEM decrypt struct+data {-# CTYPE "botan/ffi.h" "struct botan_pk_op_kem_decrypt_struct" #-} BotanPKOpKEMDecryptStruct++-- | Botan KEM decrypt object+newtype {-# CTYPE "botan/ffi.h" "botan_pk_op_kem_decrypt_t" #-} BotanPKOpKEMDecrypt+ = MkBotanPKOpKEMDecrypt { runBotanPKOpKEMDecrypt :: Ptr BotanPKOpKEMDecryptStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a KEM decrypt object+foreign import capi safe "botan/ffi.h &botan_pk_op_kem_decrypt_destroy"+ botan_pk_op_kem_decrypt_destroy+ :: FinalizerPtr BotanPKOpKEMDecryptStruct++foreign import capi safe "botan/ffi.h botan_pk_op_kem_decrypt_create"+ botan_pk_op_kem_decrypt_create+ :: Ptr BotanPKOpKEMDecrypt -- ^ __op__+ -> BotanPrivKey -- ^ __key__+ -> ConstPtr CChar -- ^ __kdf__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_kem_decrypt_shared_key_length"+ botan_pk_op_kem_decrypt_shared_key_length+ :: BotanPKOpKEMDecrypt -- ^ __op__+ -> CSize -- ^ __desired_shared_key_length__+ -> Ptr CSize -- ^ __output_shared_key_length__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_kem_decrypt_shared_key"+ botan_pk_op_kem_decrypt_shared_key+ :: BotanPKOpKEMDecrypt -- ^ __op__+ -> ConstPtr Word8 -- ^ __salt[]__+ -> CSize -- ^ __salt_len__+ -> ConstPtr Word8 -- ^ __encapsulated_key[]__+ -> CSize -- ^ __encapsulated_key_len__+ -> CSize -- ^ __desired_shared_key_len__+ -> Ptr Word8 -- ^ __shared_key[]__+ -> Ptr CSize -- ^ __shared_key_len__+ -> IO CInt
+ src/Botan/Bindings/PubKey/RSA.hs view
@@ -0,0 +1,47 @@+{-|+Module : Botan.Bindings.RSA+Description : Algorithm specific key operations: RSA+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.RSA where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++foreign import capi safe "botan/ffi.h botan_privkey_load_rsa"+ botan_privkey_load_rsa+ :: Ptr BotanPrivKey -- ^ __key__+ -> BotanMP -- ^ __p__+ -> BotanMP -- ^ __q__+ -> BotanMP -- ^ __e__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_load_rsa_pkcs1"+ botan_privkey_load_rsa_pkcs1+ :: Ptr BotanPrivKey -- ^ __key__+ -> ConstPtr Word8 -- ^ __bits[]__+ -> CSize -- ^ __len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_rsa_get_privkey"+ botan_privkey_rsa_get_privkey+ :: BotanPrivKey -- ^ __rsa_key__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_load_rsa"+ botan_pubkey_load_rsa+ :: Ptr BotanPubKey -- ^ __key__+ -> BotanMP -- ^ __n__+ -> BotanMP -- ^ __e__+ -> IO CInt
+ src/Botan/Bindings/PubKey/SM2.hs view
@@ -0,0 +1,42 @@+{-|+Module : Botan.Bindings.PubKey.SM2+Description : Algorithm specific key operations: SM2+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}+++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.SM2 where++import Botan.Bindings.MPI+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++foreign import capi safe "botan/ffi.h botan_pubkey_load_sm2"+ botan_pubkey_load_sm2+ :: Ptr BotanPubKey -- ^ __key__+ -> BotanMP -- ^ __public_x__+ -> BotanMP -- ^ __public_y__+ -> ConstPtr CChar -- ^ __curve_name__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_load_sm2"+ botan_privkey_load_sm2+ :: Ptr BotanPrivKey -- ^ __key__+ -> BotanMP -- ^ __scalar__+ -> ConstPtr CChar -- ^ __curve_name__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_sm2_compute_za"+ botan_pubkey_sm2_compute_za+ :: Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> ConstPtr CChar -- ^ __ident__+ -> ConstPtr CChar -- ^ __hash_algo__+ -> BotanPubKey -- ^ __key__+ -> IO CInt
+ src/Botan/Bindings/PubKey/Sign.hsc view
@@ -0,0 +1,70 @@+{-|+Module : Botan.Bindings.Sign+Description : Signature Generation+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.Sign where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.RNG++#include <botan/ffi.h>++-- | Opaque sign struct+data {-# CTYPE "botan/ffi.h" "struct botan_pk_op_sign_struct" #-} BotanPKOpSignStruct++-- | Botan sign object+newtype {-# CTYPE "botan/ffi.h" "botan_pk_op_sign_t" #-} BotanPKOpSign+ = MkBotanPKOpSign { runBotanPKOpSign :: Ptr BotanPKOpSignStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a sign object+foreign import capi safe "botan/ffi.h &botan_pk_op_sign_destroy"+ botan_pk_op_sign_destroy+ :: FinalizerPtr BotanPKOpSignStruct++-- NOTE: These are separate flags from BOTAN_PRIVKEY_EXPORT_FLAG_DER and BOTAN_PRIVKEY_EXPORT_FLAG_PEM+-- The correct default flag would be BOTAN_PUBKEY_STD_FORMAT_SIGNATURE, and is not necessarily+-- indicative of PEM encoding+pattern BOTAN_PUBKEY_STD_FORMAT_SIGNATURE -- ^ Not an actual flag+ , BOTAN_PUBKEY_DER_FORMAT_SIGNATURE+ :: (Eq a, Num a) => a+pattern BOTAN_PUBKEY_STD_FORMAT_SIGNATURE = 0+pattern BOTAN_PUBKEY_DER_FORMAT_SIGNATURE = #const BOTAN_PUBKEY_DER_FORMAT_SIGNATURE++foreign import capi safe "botan/ffi.h botan_pk_op_sign_create"+ botan_pk_op_sign_create+ :: Ptr BotanPKOpSign -- ^ __op__+ -> BotanPrivKey -- ^ __key__+ -> ConstPtr CChar -- ^ __hash_and_padding__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_sign_output_length"+ botan_pk_op_sign_output_length+ :: BotanPKOpSign -- ^ __op__+ -> Ptr CSize -- ^ __olen__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_sign_update"+ botan_pk_op_sign_update+ :: BotanPKOpSign -- ^ __op__+ -> ConstPtr Word8 -- ^ __in[]__+ -> CSize -- ^ __in_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_sign_finish"+ botan_pk_op_sign_finish+ :: BotanPKOpSign -- ^ __op__+ -> BotanRNG -- ^ __rng__+ -> Ptr Word8 -- ^ __sig[]__+ -> Ptr CSize -- ^ __sig_len__+ -> IO CInt
+ src/Botan/Bindings/PubKey/Verify.hsc view
@@ -0,0 +1,62 @@+{-|+Module : Botan.Bindings.Verify+Description : Signature Verification+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.Verify+( BotanPKOpVerifyStruct+, BotanPKOpVerify(..)+, botan_pk_op_verify_destroy+, botan_pk_op_verify_create+, botan_pk_op_verify_update+, botan_pk_op_verify_finish+, pattern BOTAN_PUBKEY_STD_FORMAT_SIGNATURE +, pattern BOTAN_PUBKEY_DER_FORMAT_SIGNATURE+) where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.PubKey.Sign++-- | Opaque verify struct+data {-# CTYPE "botan/ffi.h" "struct botan_pk_op_verify_struct" #-} BotanPKOpVerifyStruct++-- | Botan verify object+newtype {-# CTYPE "botan/ffi.h" "botan_pk_op_verify_t" #-} BotanPKOpVerify+ = MkBotanPKOpVerify { runBotanPKOpVerify :: Ptr BotanPKOpVerifyStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a verify object+foreign import capi safe "botan/ffi.h &botan_pk_op_verify_destroy"+ botan_pk_op_verify_destroy+ :: FinalizerPtr BotanPKOpVerifyStruct++-- | Uses the same flags as botan_pk_op_sign_create+foreign import capi safe "botan/ffi.h botan_pk_op_verify_create"+ botan_pk_op_verify_create+ :: Ptr BotanPKOpVerify -- ^ __op__+ -> BotanPubKey -- ^ __key__+ -> ConstPtr CChar -- ^ __hash_and_padding__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_verify_update"+ botan_pk_op_verify_update+ :: BotanPKOpVerify -- ^ __op__+ -> ConstPtr Word8 -- ^ __in[]__+ -> CSize -- ^ __in_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pk_op_verify_finish"+ botan_pk_op_verify_finish+ :: BotanPKOpVerify -- ^ __op__+ -> ConstPtr Word8 -- ^ __sig[]__+ -> CSize -- ^ __sig_len__+ -> IO CInt
+ src/Botan/Bindings/PubKey/X25519.hs view
@@ -0,0 +1,40 @@+{-|+Module : Botan.Bindings.X25519+Description : Algorithm specific key operations: X25519+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PubKey.X25519 where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey++foreign import capi safe "botan/ffi.h botan_privkey_load_x25519"+ botan_privkey_load_x25519+ :: Ptr BotanPrivKey -- ^ __key__+ -> ConstPtr Word8 -- ^ __privkey[32]__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_load_x25519"+ botan_pubkey_load_x25519+ :: Ptr BotanPubKey -- ^ __key__+ -> ConstPtr Word8 -- ^ __pubkey[32]__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_privkey_x25519_get_privkey"+ botan_privkey_x25519_get_privkey+ :: BotanPrivKey -- ^ __key__+ -> Ptr Word8 -- ^ __output[32]__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_pubkey_x25519_get_pubkey"+ botan_pubkey_x25519_get_pubkey+ :: BotanPubKey -- ^ __key__+ -> Ptr Word8 -- ^ __pubkey[32]__+ -> IO CInt
+ src/Botan/Bindings/PwdHash.hs view
@@ -0,0 +1,68 @@+{-|+Module : Botan.Bindings.PwdHash+Description : Password hashing+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++Derive a key from a passphrase+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.PwdHash where++import Botan.Bindings.Prelude++pattern BOTAN_PBKDF_PBKDF2+ , BOTAN_PBKDF_SCRYPT+ , BOTAN_PBKDF_ARGON2D+ , BOTAN_PBKDF_ARGON2I+ , BOTAN_PBKDF_ARGON2ID+ , BOTAN_PBKDF_BCRYPT_PBKDF+ , BOTAN_PBKDF_OPENPGP_S2K+ :: (Eq a, IsString a) => a++pattern BOTAN_PBKDF_PBKDF2 = "PBKDF2"+pattern BOTAN_PBKDF_SCRYPT = "Scrypt"+pattern BOTAN_PBKDF_ARGON2D = "Argon2d"+pattern BOTAN_PBKDF_ARGON2I = "Argon2i"+pattern BOTAN_PBKDF_ARGON2ID = "Argon2id"+pattern BOTAN_PBKDF_BCRYPT_PBKDF = "Bcrypt-PBKDF"+pattern BOTAN_PBKDF_OPENPGP_S2K = "OpenPGP-S2K"++-- | Derive a key from a passphrase using algorithm-specific parameters+foreign import capi safe "botan/ffi.h botan_pwdhash"+ botan_pwdhash+ :: ConstPtr CChar -- ^ __algo__: PBKDF algorithm, e.g., "PBKDF2(SHA-256)" or "Scrypt"+ -> CSize -- ^ __param1__: the first PBKDF algorithm parameter+ -> CSize -- ^ __param2__: the second PBKDF algorithm parameter (may be zero if unneeded)+ -> CSize -- ^ __param3__: the third PBKDF algorithm parameter (may be zero if unneeded)+ -> Ptr Word8 -- ^ __out[]__: buffer to store the derived key, must be of out_len bytes+ -> CSize -- ^ __out_len__: the desired length of the key to produce+ -> ConstPtr CChar -- ^ __passphrase__: the password to derive the key from+ -> CSize -- ^ __passphrase_len__: if > 0, specifies length of password. If len == 0, then+ -- strlen will be called on passphrase to compute the length.+ -> ConstPtr Word8 -- ^ __salt[]__: a randomly chosen salt+ -> CSize -- ^ __salt_len__: length of salt in bytes+ -> IO CInt -- ^ 0 on success, a negative value on failure+++-- | Derive a key from a passphrase using parameters generated over a specific duration+foreign import capi safe "botan/ffi.h botan_pwdhash_timed"+ botan_pwdhash_timed+ :: ConstPtr CChar -- ^ __algo__: PBKDF algorithm, e.g., "Scrypt" or "PBKDF2(SHA-256)"+ -> Word32 -- ^ __msec__: the desired runtime in milliseconds+ -> Ptr CSize -- ^ __param1__: will be set to the first password hash parameter+ -> Ptr CSize -- ^ __param2__: will be set to the second password hash parameter+ -> Ptr CSize -- ^ __param3__: will be set to the third password hash parameter+ -> Ptr Word8 -- ^ __out[]__: buffer to store the derived key, must be of out_len bytes+ -> CSize -- ^ __out_len__: the desired length of the key to produce+ -> ConstPtr CChar -- ^ __passphrase__: the password to derive the key from+ -> CSize -- ^ __passphrase_len__: if > 0, specifies length of password. If len == 0, then+ -- strlen will be called on passphrase to compute the length.+ -> ConstPtr Word8 -- ^ __salt[]__: a randomly chosen salt+ -> CSize -- ^ __salt_len__: length of salt in bytes+ -> IO CInt -- ^ 0 on success, a negative value on failure
+ src/Botan/Bindings/RNG.hs view
@@ -0,0 +1,150 @@+{-|+Module : Botan.Bindings.RNG+Description : Random number generators+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.RNG where+import Botan.Bindings.Prelude++-- | Opaque RNG struct+data {-# CTYPE "botan/ffi.h" "struct botan_rng_struct" #-} BotanRNGStruct++-- | Botan RNG object+newtype {-# CTYPE "botan/ffi.h" "botan_rng_t" #-} BotanRNG+ = MkBotanRNG { runBotanRNG :: Ptr BotanRNGStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Frees all resources of the random number generator object+foreign import capi safe "botan/ffi.h &botan_rng_destroy"+ botan_rng_destroy+ :: FinalizerPtr BotanRNGStruct++-- WARNING: Not real botan constants, values are taken from documentation / source code.+-- TODO: Maybe move to Botan.Low.RNG+pattern BOTAN_RNG_TYPE_SYSTEM -- ^ system RNG+ , BOTAN_RNG_TYPE_USER -- ^ userspace RNG+ , BOTAN_RNG_TYPE_USER_THREADSAFE -- ^ userspace RNG, with internal locking+ , BOTAN_RNG_TYPE_RDRAND -- ^ directly read RDRAND+ :: (Eq a, IsString a) => a+pattern BOTAN_RNG_TYPE_SYSTEM = "system"+pattern BOTAN_RNG_TYPE_USER = "user"+pattern BOTAN_RNG_TYPE_USER_THREADSAFE = "user-threadsafe"+pattern BOTAN_RNG_TYPE_RDRAND = "rdrand"++{- |+Initialize a random number generator object++rng_type has the possible values:++ - "system": system RNG+ + - "user": userspace RNG+ + - "user-threadsafe": userspace RNG, with internal locking+ + - "rdrand": directly read RDRAND++Set rng_type to null to let the library choose some default.+-}+foreign import capi safe "botan/ffi.h botan_rng_init"+ botan_rng_init+ :: Ptr BotanRNG -- ^ __rng__+ -> ConstPtr CChar -- ^ __rng_type__: type of the rng+ -> IO CInt -- ^ 0 if success, else error code++-- | Callback for getting random bytes from the rng, return 0 for success+type BotanRNGGetCallback ctx+ = Ptr ctx -- ^ __context__+ -> Ptr Word8 -- ^ __out__+ -> CSize -- ^ __out_len__+ -> IO CInt++-- NOTE: "Wrapper stubs can't be used with CApiFFI."+foreign import ccall "wrapper"+ mallocBotanRNGGetCallbackFunPtr+ :: BotanRNGGetCallback ctx+ -> IO (FunPtr (BotanRNGGetCallback ctx))++-- | Callback for adding entropy to the rng, return 0 for success+type BotanRNGAddEntropyCallback ctx+ = Ptr ctx -- ^ __context__+ -> ConstPtr Word8 -- ^ __input[]__+ -> CSize -- ^ __length__+ -> IO CInt++-- NOTE: "Wrapper stubs can't be used with CApiFFI."+foreign import ccall "wrapper"+ mallocBotanRNGAddEntropyCallbackFunPtr+ :: BotanRNGAddEntropyCallback ctx+ -> IO (FunPtr (BotanRNGAddEntropyCallback ctx))++-- | Callback called when rng is destroyed+type BotanRNGDestroyCallback ctx+ = Ptr ctx -- ^ __context__+ -> IO ()++-- NOTE: "Wrapper stubs can't be used with CApiFFI."+foreign import ccall "wrapper"+ mallocBotanRNGDestroyCallbackFunPtr+ :: BotanRNGDestroyCallback ctx+ -> IO (FunPtr (BotanRNGDestroyCallback ctx))++-- | Initialize a custom random number generator from a set of callback functions+foreign import capi safe "botan/ffi.h botan_rng_init_custom"+ botan_rng_init_custom+ :: Ptr BotanRNG -- ^ __rng_out__+ -> ConstPtr CChar -- ^ __rng_name__: name of the rng+ -> Ptr ctx -- ^ __context__: an application-specific context passed to the callback functions+ -> FunPtr (BotanRNGGetCallback ctx) -- ^ __get_cb__+ -> FunPtr (BotanRNGAddEntropyCallback ctx) -- ^ __add_entropy_cb__: may be NULL+ -> FunPtr (BotanRNGDestroyCallback ctx) -- ^ __destroy_cb__: may be NULL+ -> IO CInt++-- | Get random bytes from a random number generators+foreign import capi safe "botan/ffi.h botan_rng_get"+ botan_rng_get+ :: BotanRNG -- ^ __rng__: rng object+ -> Ptr Word8 -- ^ __out__: output buffer of size out_len+ -> CSize -- ^ __out_len__: number of requested bytes+ -> IO CInt -- ^ 0 on success, negative on failure++-- | Get random bytes from system random number generator+foreign import capi safe "botan/ffi.h botan_system_rng_get"+ botan_system_rng_get+ :: Ptr Word8 -- ^ __out__: output buffer of size out_len+ -> CSize -- ^ __out_len__: number of requested bytes+ -> IO CInt -- ^ 0 on success, negative on failure++{- |+Reseed a random number generator++Uses the System_RNG as a seed generator.+-}+foreign import capi safe "botan/ffi.h botan_rng_reseed"+ botan_rng_reseed+ :: BotanRNG -- ^ __rng__: rng object+ -> CSize -- ^ __bits__: number of bits to reseed with+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Reseed a random number generator+foreign import capi safe "botan/ffi.h botan_rng_reseed_from_rng"+ botan_rng_reseed_from_rng+ :: BotanRNG -- ^ __rng__: rng object+ -> BotanRNG -- ^ __source_rng__: the rng that will be read from+ -> CSize -- ^ __bits__: number of bits to reseed with+ -> IO CInt -- ^ 0 on success, a negative value on failure++-- | Add some seed material to a random number generator+foreign import capi safe "botan/ffi.h botan_rng_add_entropy"+ botan_rng_add_entropy+ :: BotanRNG -- ^ __rng__: rng object+ -> ConstPtr Word8 -- ^ __entropy__: the data to add+ -> CSize -- ^ __entropy_len__: length of entropy buffer+ -> IO CInt -- ^ 0 on success, a negative value on failure
+ src/Botan/Bindings/SRP6.hs view
@@ -0,0 +1,117 @@+{-|+Module : Botan.Bindings.SRP6+Description : Secure remote password+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++The library contains an implementation of the SRP6-a password+authenticated key exchange protocol.++A SRP client provides what is called a SRP verifier to the server.+This verifier is based on a password, but the password cannot be+easily derived from the verifier (however brute force attacks are+possible). Later, the client and server can perform an SRP exchange,+which results in a shared secret key. This key can be used for+mutual authentication and/or encryption.++SRP works in a discrete logarithm group. Special parameter sets for+SRP6 are defined, denoted in the library as “modp/srp/<size>”, for+example “modp/srp/2048”.++Warning++While knowledge of the verifier does not easily allow an attacker to+get the raw password, they could still use the verifier to impersonate+the server to the client, so verifiers should be protected as carefully+as a plaintext password would be.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.SRP6 where++import Botan.Bindings.Prelude+import Botan.Bindings.RNG++-- | Opaque SRP-6 server session struct+data {-# CTYPE "botan/ffi.h" "struct botan_srp6_server_session_struct" #-} BotanSRP6ServerSessionStruct++-- | Botan SRP-6 server session object+newtype {-# CTYPE "botan/ffi.h" "botan_srp6_server_session_t" #-} BotanSRP6ServerSession+ = MkBotanSRP6ServerSession { runBotanSRP6ServerSession :: Ptr BotanSRP6ServerSessionStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Frees all resources of the SRP-6 server session object+foreign import capi safe "botan/ffi.h &botan_srp6_server_session_destroy"+ botan_srp6_server_session_destroy+ :: FinalizerPtr BotanSRP6ServerSessionStruct++-- | Initialize an SRP-6 server session object+foreign import capi safe "botan/ffi.h botan_srp6_server_session_init"+ botan_srp6_server_session_init+ :: Ptr BotanSRP6ServerSession -- ^ __srp6__: SRP-6 server session object+ -> IO CInt++-- | SRP-6 Server side step 1: Generate a server B-value+foreign import capi safe "botan/ffi.h botan_srp6_server_session_step1"+ botan_srp6_server_session_step1+ :: BotanSRP6ServerSession -- ^ __srp6__: SRP-6 server session object+ -> ConstPtr Word8 -- ^ __verifier[]__: the verification value saved from client registration+ -> CSize -- ^ __verifier_len__: SRP-6 verifier value length+ -> ConstPtr CChar -- ^ __group_id__: the SRP group id+ -> ConstPtr CChar -- ^ __hash_id__: the SRP hash in use+ -> BotanRNG -- ^ __rng_obj__: a random number generator object+ -> Ptr Word8 -- ^ __B_pub[]__: out buffer to store the SRP-6 B value+ -> Ptr CSize -- ^ __B_pub_len__: SRP-6 B value length+ -> IO CInt -- ^ 0 on success, negative on failure++-- | SRP-6 Server side step 2: Generate the server shared key+foreign import capi safe "botan/ffi.h botan_srp6_server_session_step2"+ botan_srp6_server_session_step2+ :: BotanSRP6ServerSession -- ^ __srp6__: SRP-6 server session object+ -> ConstPtr Word8 -- ^ __A[]__: the client's value+ -> CSize -- ^ __A_len__: the client's value length+ -> Ptr Word8 -- ^ __key[]__: out buffer to store the symmetric key value+ -> Ptr CSize -- ^ __key_len__: symmetric key length+ -> IO CInt -- ^ 0 on success, negative on failure++-- | SRP-6 Client side step 1: Generate a new SRP-6 verifier+foreign import capi safe "botan/ffi.h botan_srp6_generate_verifier"+ botan_srp6_generate_verifier+ :: ConstPtr CChar -- ^ __identifier__: a username or other client identifier+ -> ConstPtr CChar -- ^ __password__: the secret used to authenticate user+ -> ConstPtr Word8 -- ^ __salt[]__: a randomly chosen value, at least 128 bits long+ -> CSize -- ^ __salt_len__: the length of salt+ -> ConstPtr CChar -- ^ __group_id__: specifies the shared SRP group+ -> ConstPtr CChar -- ^ __hash_id__: specifies a secure hash function+ -> Ptr Word8 -- ^ __verifier[]__: out buffer to store the SRP-6 verifier value+ -> Ptr CSize -- ^ __verifier_len__: SRP-6 verifier value length+ -> IO CInt -- ^ 0 on success, negative on failure++-- | SRP6a Client side step 2: Generate a client A-value and the client shared key+foreign import capi safe "botan/ffi.h botan_srp6_client_agree"+ botan_srp6_client_agree+ :: ConstPtr CChar -- ^ __username__: the username we are attempting login for+ -> ConstPtr CChar -- ^ __password__: the password we are attempting to use+ -> ConstPtr CChar -- ^ __group_id__: specifies the shared SRP group+ -> ConstPtr CChar -- ^ __hash_id__: specifies a secure hash function+ -> ConstPtr Word8 -- ^ __salt[]__: is the salt value sent by the server+ -> CSize -- ^ __salt_len__: the length of salt+ -> ConstPtr Word8 -- ^ __uint8_t__: B[] is the server's public value+ -> CSize -- ^ __B_len__: is the server's public value length+ -> BotanRNG -- ^ __rng_obj__: is a random number generator object+ -> Ptr Word8 -- ^ __A[]__: out buffer to store the SRP-6 A value+ -> Ptr CSize -- ^ __A_len__: SRP-6 A verifier value length+ -> Ptr Word8 -- ^ __K[]__: out buffer to store the symmetric value+ -> Ptr CSize -- ^ __K_len__: symmetric key length+ -> IO CInt -- ^ 0 on success, negative on failure++-- | Return the size, in bytes, of the prime associated with group_id+foreign import capi safe "botan/ffi.h botan_srp6_group_size"+ botan_srp6_group_size+ :: ConstPtr CChar -- ^ __group_id__+ -> Ptr CSize -- ^ __group_p_bytes__+ -> IO CInt
+ src/Botan/Bindings/TOTP.hs view
@@ -0,0 +1,89 @@+{-|+Module : Botan.Bindings.TOTP+Description : Time-based one time passwords+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++One time password schemes are a user authentication method that+relies on a fixed secret key which is used to derive a sequence+of short passwords, each of which is accepted only once. Commonly+this is used to implement two-factor authentication (2FA), where+the user authenticates using both a conventional password (or a+public key signature) and an OTP generated by a small device such+as a mobile phone.++Botan implements the HOTP and TOTP schemes from RFC 4226 and 6238.++Since the range of possible OTPs is quite small, applications must+rate limit OTP authentication attempts to some small number per +second. Otherwise an attacker could quickly try all 1000000 6-digit+OTPs in a brief amount of time.++HOTP generates OTPs that are a short numeric sequence, between 6+and 8 digits (most applications use 6 digits), created using the+HMAC of a 64-bit counter value. If the counter ever repeats the+OTP will also repeat, thus both parties must assure the counter+only increments and is never repeated or decremented. Thus both+client and server must keep track of the next counter expected.++Anyone with access to the client-specific secret key can authenticate+as that client, so it should be treated with the same security+consideration as would be given to any other symmetric key or+plaintext password.++TOTP is based on the same algorithm as HOTP, but instead of a+counter a timestamp is used.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.TOTP where++import Botan.Bindings.Prelude++-- NOTE: RFC 6238++-- | Opaque TOTP struct+data {-# CTYPE "botan/ffi.h" "struct botan_totp_struct" #-} BotanTOTPStruct++-- | Botan TOTP object+newtype {-# CTYPE "botan/ffi.h" "botan_totp_t" #-} BotanTOTP+ = MkBotanTOTP { runBotanTOTP :: Ptr BotanTOTPStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a TOTP instance+foreign import capi safe "botan/ffi.h &botan_totp_destroy"+ botan_totp_destroy+ :: FinalizerPtr BotanTOTPStruct++-- | Initialize a TOTP instance+foreign import capi safe "botan/ffi.h botan_totp_init"+ botan_totp_init+ :: Ptr BotanTOTP -- ^ __totp__+ -> ConstPtr Word8 -- ^ __key[]__+ -> CSize -- ^ __key_len__+ -> ConstPtr CChar -- ^ __hash_algo__+ -> CSize -- ^ __digits__+ -> CSize -- ^ __time_step__+ -> IO CInt++-- | Generate a TOTP code for the provided timestamp+foreign import capi safe "botan/ffi.h botan_totp_generate"+ botan_totp_generate+ :: BotanTOTP -- ^ __totp__: the TOTP object+ -> Ptr Word32 -- ^ __totp_code__: the OTP code will be written here+ -> Word64 -- ^ __timestamp__: the current local timestamp+ -> IO CInt++-- | Verify a TOTP code+foreign import capi safe "botan/ffi.h botan_totp_check"+ botan_totp_check+ :: BotanTOTP -- ^ __totp__: the TOTP object+ -> Word32 -- ^ __totp_code__: the presented OTP+ -> Word64 -- ^ __timestamp__: the current local timestamp+ -> CSize -- ^ __acceptable_clock_drift__: specifies the acceptable amount+ -- of clock drift (in terms of time steps) between the two hosts.+ -> IO CInt
+ src/Botan/Bindings/Utility.hsc view
@@ -0,0 +1,70 @@+{-|+Module : Botan.Bindings.Utility+Description : Utility functions+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.Utility where++import Botan.Bindings.Prelude++#include <botan/ffi.h>++-- | Returns 0 if x[0..len] == y[0..len], -1 otherwise.+foreign import capi safe "botan/ffi.h botan_constant_time_compare"+ botan_constant_time_compare+ :: ConstPtr Word8 -- ^ __x__+ -> ConstPtr Word8 -- ^ __y__+ -> CSize -- ^ __len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_scrub_mem"+ botan_scrub_mem+ :: Ptr a -- ^ __mem__+ -> CSize -- ^ __bytes__+ -> IO CInt++pattern BOTAN_FFI_HEX_UPPER_CASE -- ^ NOTE: Not an actual flag+ , BOTAN_FFI_HEX_LOWER_CASE+ :: (Eq a, Num a) => a++pattern BOTAN_FFI_HEX_UPPER_CASE = 0+pattern BOTAN_FFI_HEX_LOWER_CASE = #const BOTAN_FFI_HEX_LOWER_CASE++foreign import capi safe "botan/ffi.h botan_hex_encode"+ botan_hex_encode+ :: ConstPtr Word8 -- ^ __x__+ -> CSize -- ^ __len__+ -> Ptr CChar -- ^ __y__+ -> Word32 -- ^ __flags__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_hex_decode"+ botan_hex_decode+ :: ConstPtr CChar -- ^ __hex_str__+ -> CSize -- ^ __in_len__+ -> Ptr Word8 -- ^ __out__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_base64_encode"+ botan_base64_encode+ :: ConstPtr Word8 -- ^ __x__+ -> CSize -- ^ __len__+ -> Ptr CChar -- ^ __out__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_base64_decode"+ botan_base64_decode+ :: ConstPtr CChar -- ^ __base64_str__+ -> CSize -- ^ __in_len__+ -> Ptr Word8 -- ^ __out__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt
+ src/Botan/Bindings/Version.hs view
@@ -0,0 +1,36 @@+{-|+Module : Botan.Bindings.Version+Description : Botan version info+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.Version where++import Botan.Bindings.Prelude++foreign import capi safe "botan/ffi.h botan_ffi_api_version"+ botan_ffi_api_version :: IO Word32++foreign import capi safe "botan/ffi.h botan_ffi_supports_api"+ botan_ffi_supports_api :: Word32 -> IO CInt++foreign import capi safe "botan/ffi.h botan_version_string"+ botan_version_string :: IO (ConstPtr CChar)++foreign import capi safe "botan/ffi.h botan_version_major"+ botan_version_major :: IO Word32++foreign import capi safe "botan/ffi.h botan_version_minor"+ botan_version_minor :: IO Word32++foreign import capi safe "botan/ffi.h botan_version_patch"+ botan_version_patch :: IO Word32++foreign import capi safe "botan/ffi.h botan_version_datestamp"+ botan_version_datestamp :: IO Word32
+ src/Botan/Bindings/View.hs view
@@ -0,0 +1,58 @@+{-|+Module : Botan.Bindings.View+Description : View functions+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.View where++import Botan.Bindings.Prelude++-- View context++-- NOTE: If the type variable proves problematic, we will revert back to Ptr Void+type BotanViewContext a = Ptr a++-- View binary++type BotanViewBinFn ctx+ = BotanViewContext ctx -- ^ __view_ctx__: some application context+ -> ConstPtr Word8 -- ^ __data__: the binary data+ -> CSize -- ^ __len__: the length of data in bytes+ -> CInt+ +type BotanViewBinCallback ctx = FunPtr (BotanViewBinFn ctx)++-- NOTE: "Wrapper stubs can't be used with CApiFFI."+foreign import ccall "wrapper"+ mallocBotanViewBinCallback+ :: BotanViewBinFn ctx+ -> IO (BotanViewBinCallback ctx)++freeBotanViewBinCallback :: BotanViewBinCallback ctx -> IO ()+freeBotanViewBinCallback = freeHaskellFunPtr++-- View string++type BotanViewStrFn ctx+ = BotanViewContext ctx -- ^ __view_ctx__: some application context+ -> ConstPtr CChar -- ^ __str__: the null terminated string+ -> CSize -- ^ __len__: the length of string *including* the null terminator+ -> CInt++type BotanViewStrCallback ctx = FunPtr (BotanViewStrFn ctx)++-- NOTE: "Wrapper stubs can't be used with CApiFFI."+foreign import ccall "wrapper"+ mallocBotanViewStrCallback+ :: BotanViewStrFn ctx+ -> IO (BotanViewStrCallback ctx)++freeBotanViewStrCallback :: BotanViewStrCallback ctx -> IO ()+freeBotanViewStrCallback = freeHaskellFunPtr
+ src/Botan/Bindings/X509.hsc view
@@ -0,0 +1,298 @@+{-|+Module : Botan.Bindings.X509+Description : X.509 Certificates and CRLs+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++A certificate is a binding between some identifying information+(called a subject) and a public key. This binding is asserted by+a signature on the certificate, which is placed there by some+authority (the issuer) that at least claims that it knows the+subject named in the certificate really “owns” the private key+corresponding to the public key in the certificate.++The major certificate format in use today is X.509v3, used for+instance in the Transport Layer Security (TLS) protocol.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.X509 where++import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.View++#include <botan/ffi.h>++-- | Opaque X509Cert struct+data {-# CTYPE "botan/ffi.h" "struct botan_x509_cert_struct" #-} BotanX509CertStruct++-- | Botan X509Cert object+newtype {-# CTYPE "botan/ffi.h" "botan_x509_cert_t" #-} BotanX509Cert+ = MkBotanX509Cert { runBotanX509Cert :: Ptr BotanX509CertStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a X509Cert instance+foreign import capi safe "botan/ffi.h &botan_x509_cert_destroy"+ botan_x509_cert_destroy+ :: FinalizerPtr BotanX509CertStruct++foreign import capi safe "botan/ffi.h botan_x509_cert_load"+ botan_x509_cert_load+ :: Ptr BotanX509Cert -- ^ __cert_obj__+ -> ConstPtr Word8 -- ^ __cert[]__+ -> CSize -- ^ __cert_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_load_file"+ botan_x509_cert_load_file+ :: Ptr BotanX509Cert -- ^ __cert_obj__+ -> ConstPtr CChar -- ^ __filename__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_dup"+ botan_x509_cert_dup+ :: Ptr BotanX509Cert -- ^ __new_cert__+ -> BotanX509Cert -- ^ __cert__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_time_starts"+ botan_x509_cert_get_time_starts+ :: BotanX509Cert -- ^ __cert__+ -> Ptr CChar -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_time_expires"+ botan_x509_cert_get_time_expires+ :: BotanX509Cert -- ^ __cert__+ -> Ptr CChar -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_not_before"+ botan_x509_cert_not_before+ :: BotanX509Cert -- ^ __cert__+ -> Ptr Word64 -- ^ __time_since_epoch__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_not_after"+ botan_x509_cert_not_after+ :: BotanX509Cert -- ^ __cert__+ -> Ptr Word64 -- ^ __time_since_epoch__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_fingerprint"+ botan_x509_cert_get_fingerprint+ :: BotanX509Cert -- ^ __cert__+ -> ConstPtr CChar -- ^ __hash__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_serial_number"+ botan_x509_cert_get_serial_number+ :: BotanX509Cert -- ^ __cert__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_authority_key_id"+ botan_x509_cert_get_authority_key_id+ :: BotanX509Cert -- ^ __cert__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_subject_key_id"+ botan_x509_cert_get_subject_key_id+ :: BotanX509Cert -- ^ __cert__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_public_key_bits"+ botan_x509_cert_get_public_key_bits+ :: BotanX509Cert -- ^ __cert__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_view_public_key_bits"+ botan_x509_cert_view_public_key_bits+ :: BotanX509Cert -- ^ __cert__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewBinCallback ctx) -- ^ __view__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_public_key"+ botan_x509_cert_get_public_key+ :: BotanX509Cert -- ^ __cert__+ -> Ptr BotanPubKey -- ^ __key__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_issuer_dn"+ botan_x509_cert_get_issuer_dn+ :: BotanX509Cert -- ^ __cert__+ -> ConstPtr CChar -- ^ __key__+ -> CSize -- ^ __index__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_get_subject_dn"+ botan_x509_cert_get_subject_dn+ :: BotanX509Cert -- ^ __cert__+ -> ConstPtr CChar -- ^ __key__+ -> CSize -- ^ __index__+ -> Ptr Word8 -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_to_string"+ botan_x509_cert_to_string+ :: BotanX509Cert -- ^ __cert__+ -> Ptr CChar -- ^ __out[]__+ -> Ptr CSize -- ^ __out_len__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_cert_view_as_string"+ botan_x509_cert_view_as_string+ :: BotanX509Cert -- ^ __cert__+ -> BotanViewContext ctx -- ^ __ctx__+ -> FunPtr (BotanViewStrCallback ctx) -- ^ __view__+ -> IO CInt++pattern NO_CONSTRAINTS+ , DIGITAL_SIGNATURE+ , NON_REPUDIATION+ , KEY_ENCIPHERMENT+ , DATA_ENCIPHERMENT+ , KEY_AGREEMENT+ , KEY_CERT_SIGN+ , CRL_SIGN+ , ENCIPHER_ONLY+ , DECIPHER_ONLY+ :: (Eq a, Num a) => a+pattern NO_CONSTRAINTS = #const NO_CONSTRAINTS+pattern DIGITAL_SIGNATURE = #const DIGITAL_SIGNATURE+pattern NON_REPUDIATION = #const NON_REPUDIATION+pattern KEY_ENCIPHERMENT = #const KEY_ENCIPHERMENT+pattern DATA_ENCIPHERMENT = #const DATA_ENCIPHERMENT+pattern KEY_AGREEMENT = #const KEY_AGREEMENT+pattern KEY_CERT_SIGN = #const KEY_CERT_SIGN+pattern CRL_SIGN = #const CRL_SIGN+pattern ENCIPHER_ONLY = #const ENCIPHER_ONLY+pattern DECIPHER_ONLY = #const DECIPHER_ONLY++foreign import capi safe "botan/ffi.h botan_x509_cert_allowed_usage"+ botan_x509_cert_allowed_usage+ :: BotanX509Cert -- ^ __cert__+ -> CUInt -- ^ __key_usage__+ -> IO CInt++{- |+Check if the certificate matches the specified hostname via alternative name or CN match.+RFC 5280 wildcards also supported.+-}+foreign import capi safe "botan/ffi.h botan_x509_cert_hostname_match"+ botan_x509_cert_hostname_match+ :: BotanX509Cert -- ^ __cert__+ -> ConstPtr CChar -- ^ __hostname__+ -> IO CInt++{- |+Returns 0 if the validation was successful, 1 if validation failed,+and negative on error. A status code with details is written to+*validation_result++Intermediates or trusted lists can be null+Trusted path can be null+-}+foreign import capi safe "botan/ffi.h botan_x509_cert_verify"+ botan_x509_cert_verify+ :: Ptr CInt -- ^ __validation_result__+ -> BotanX509Cert -- ^ __cert__+ -> ConstPtr BotanX509Cert -- ^ __intermediates__+ -> CSize -- ^ __intermediates_len__+ -> ConstPtr BotanX509Cert -- ^ __trusted__+ -> CSize -- ^ __trusted_len__+ -> ConstPtr CChar -- ^ __trusted_path__+ -> CSize -- ^ __required_strength__+ -> ConstPtr CChar -- ^ __hostname__+ -> Word64 -- ^ __reference_time__+ -> IO CInt++{- |+Returns a pointer to a static character string explaining the status code,+or else NULL if unknown.+-}+foreign import capi safe "botan/ffi.h botan_x509_cert_validation_status"+ botan_x509_cert_validation_status+ :: CInt -- ^ __code__+ -> IO (ConstPtr CChar)++{-+X.509 CRL+-}+-- TODO: Move to X509.CRL++-- | Opaque X509CRL struct+data {-# CTYPE "botan/ffi.h" "struct botan_x509_crl_struct" #-} BotanX509CRLStruct++-- | Botan X509CRL object+newtype {-# CTYPE "botan/ffi.h" "botan_x509_crl_t" #-} BotanX509CRL+ = MkBotanX509CRL { runBotanX509CRL :: Ptr BotanX509CRLStruct }+ deriving newtype (Eq, Ord, Storable)++-- | Destroy a X509CRL instance+foreign import capi safe "botan/ffi.h &botan_x509_crl_destroy"+ botan_x509_crl_destroy+ :: FinalizerPtr BotanX509CRLStruct++foreign import capi safe "botan/ffi.h botan_x509_crl_load_file"+ botan_x509_crl_load_file+ :: Ptr BotanX509CRL -- ^ __crl_obj__+ -> ConstPtr CChar -- ^ __crl_path__+ -> IO CInt++foreign import capi safe "botan/ffi.h botan_x509_crl_load"+ botan_x509_crl_load+ :: Ptr BotanX509CRL -- ^ __crl_obj__+ -> ConstPtr Word8 -- ^ __crl_bits[]__+ -> CSize -- ^ __crl_bits_len__+ -> IO CInt++{- |+Given a CRL and a certificate,+check if the certificate is revoked on that particular CRL+-}+foreign import capi safe "botan/ffi.h botan_x509_is_revoked"+ botan_x509_is_revoked+ :: BotanX509CRL -- ^ __crl__+ -> BotanX509Cert -- ^ __cert__+ -> IO CInt++{- |+Different flavor of `botan_x509_cert_verify`, supports revocation lists.+CRLs are passed as an array, same as intermediates and trusted CAs+-}+foreign import capi safe "botan/ffi.h botan_x509_cert_verify_with_crl"+ botan_x509_cert_verify_with_crl+ :: Ptr CInt -- ^ __validation_result__+ -> BotanX509Cert -- ^ __cert__+ -> ConstPtr BotanX509Cert -- ^ __intermediates__+ -> CSize -- ^ __intermediates_len__+ -> ConstPtr BotanX509Cert -- ^ __trusted__+ -> CSize -- ^ __trusted_len__+ -> ConstPtr BotanX509CRL -- ^ __crls__+ -> CSize -- ^ __crls_len__+ -> ConstPtr CChar -- ^ __trusted_path__+ -> CSize -- ^ __required_strength__+ -> ConstPtr CChar -- ^ __hostname__+ -> Word64 -- ^ __reference_time__+ -> IO CInt
+ src/Botan/Bindings/X509/CA.hs view
@@ -0,0 +1,89 @@+module Botan.Bindings.X509.CA where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+import Botan.Bindings.MPI+import Botan.Bindings.PubKey+import Botan.Bindings.PubKey.Sign+import Botan.Bindings.RNG+import Botan.Bindings.X509+import Botan.Bindings.X509.CSR+import Botan.Bindings.X509.Extensions+import Botan.Bindings.X509.Options++-- Certificate Authority+data X509CAStruct+type X509CAPtr = Ptr X509CAStruct++foreign import ccall unsafe botan_x509_ca_create+ :: Ptr X509CAPtr+ -> X509CertPtr+ -> PrivKeyPtr+ -> Ptr CChar+ -> RNGPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_ca_create_padding+ :: Ptr X509CAPtr+ -> X509CertPtr+ -> PrivKeyPtr+ -> Ptr CChar+ -> Ptr CChar+ -> RNGPtr+ -> IO BotanErrorCode++foreign import ccall unsafe "&botan_x509_ca_destroy" botan_x509_ca_destroy :: FinalizerPtr X509CAStruct++foreign import ccall unsafe botan_x509_ca_sign_request+ :: Ptr X509CertPtr+ -> X509CAPtr+ -> X509CSRPtr+ -> RNGPtr+ -> Word64+ -> Word64+ -> IO BotanErrorCode++-- foreign import ccall unsafe botan_x509_ca_sign_request_serial+-- :: Ptr X509CertPtr+-- -> X509CAPtr+-- -> X509CSRPtr+-- -> RNGPtr+-- -> MPPtr+-- -> Word64+-- -> Word64+-- -> IO BotanErrorCode++-- foreign import ccall unsafe botan_x509_ca_make_cert+-- :: Ptr X509CertPtr+-- -> SignPtr+-- -> RNGPtr+-- -> MPPtr+-- -> Ptr CChar+-- -> PubKeyPtr+-- -> Word64+-- -> Word64+-- -> Ptr Word8 -> CSize+-- -> Ptr Word8 -> CSize+-- -> X509ExtensionsPtr+-- -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_ca_make_cert_serial+ :: Ptr X509CertPtr+ -> SignPtr+ -> RNGPtr+ -> MPPtr+ -> Ptr CChar+ -> PubKeyPtr+ -> Word64+ -> Word64+ -> Ptr Word8 -> CSize+ -> Ptr Word8 -> CSize+ -> X509ExtensionsPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_ca_choose_extensions+ :: Ptr X509ExtensionsPtr+ -> X509CSRPtr+ -> X509CertPtr+ -> Ptr CChar+ -> IO BotanErrorCode
+ src/Botan/Bindings/X509/CRL.hs view
@@ -0,0 +1,142 @@+module Botan.Bindings.X509.CRL where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+import Botan.Bindings.X509+import Botan.Bindings.X509.Extensions+++--+-- Certificate Revocation List+--+-- TODO: Eventually move the read-only CRL functions into here++{-+data X509CRLStruct+type X509CRLPtr = Ptr X509CRLStruct++foreign import ccall unsafe botan_x509_crl_load :: Ptr X509CRLPtr -> Ptr Word8 -> CSize -> IO BotanErrorCode+foreign import ccall unsafe botan_x509_crl_load_file :: Ptr X509CRLPtr -> Ptr CChar -> IO BotanErrorCode+foreign import ccall unsafe "&botan_x509_crl_destroy" botan_x509_crl_destroy :: FinalizerPtr X509CRLStruct+-- NOTE: Need to rename botan_x509_is_revoked to botan_x509_crl_is_revoked first+foreign import ccall unsafe botan_x509_crl_is_revoked :: X509CRLPtr -> X509CertPtr -> IO BotanErrorCode+-}++foreign import ccall unsafe botan_x509_crl_get_revoked+ :: Ptr X509CRLEntryPtr -> Ptr CSize + -> X509CRLPtr+ -> IO BotanErrorCode++-- NOTE: If we were to follow the pattern set in `botan_x509_cert_get_issuer_dn`+-- then this would merely be an accessor for a single value using key + index)+-- NOTE: We're keeping our own return-value-first style still though so keep that+-- difference in mind+foreign import ccall unsafe botan_x509_crl_get_issuer_dn+ :: Ptr Word8 -> Ptr CSize+ -> X509CRLPtr+ -> Ptr CChar+ -> CSize+ -> IO BotanErrorCode+-- With actual DN objects, we could just return the object:+{-+foreign import ccall unsafe botan_x509_crl_issuer_dn+ :: Ptr X509DNPtr+ -> X509CRLPtr+ -> IO BotanErrorCode+-}+-- Probably should create a new pattern using botan_foo_get_dn_attribute(?)+-- (make consistent with DN object accessors) and botan_foo_get_dn_object++foreign import ccall unsafe botan_x509_crl_extensions+ :: Ptr X509ExtensionsPtr+ -> X509CRLPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_authority_key_id+ :: Ptr Word8 -> Ptr CSize+ -> X509CRLPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_serial_number+ :: Ptr Word32+ -> X509CRLPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_this_update+ :: Ptr Word64+ -> X509CRLPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_next_update+ :: Ptr Word64+ -> X509CRLPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_issuing_distribution_point+ :: Ptr Word8 -> Ptr CSize+ -> X509CRLPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_create_der+ :: Ptr X509CRLPtr+ -> Ptr Word8 -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_create+ :: Ptr X509CRLPtr+ -> Ptr Word8 -> CSize -- Encodeed Issuer DN, not DN object+ -> Word64 -- this update+ -> Word64 -- next update+ -> Ptr X509CRLEntryPtr -> CSize -- Entries+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_add_entry+ :: X509CRLPtr+ -> X509CRLEntryPtr+ -> IO BotanErrorCode++-- NOTE: A convenience function+foreign import ccall unsafe botan_x509_crl_revoke_cert+ :: X509CRLPtr+ -> X509CertPtr+ -> Word32 -- Reason+ -> IO BotanErrorCode+ +--+-- Certificate Revocation List Entry+--++data X509CRLEntryStruct+type X509CRLEntryPtr = Ptr X509CRLEntryStruct+-- TODO: These functions are only bound to declarations, and the functions are currently not implemented+-- Do not use them yet, it will just crash++foreign import ccall unsafe "&botan_x509_crl_entry_destroy" botan_x509_crl_entry_destroy :: FinalizerPtr X509CRLEntryStruct++foreign import ccall unsafe botan_x509_crl_entry_create+ :: Ptr X509CRLEntryPtr+ -> X509CertPtr+ -> Word32 -- Reason+ -> IO BotanErrorCode++-- TODO: CRL_Entry PEM / BER encode / decode (and for CRL too)++foreign import ccall unsafe botan_x509_crl_entry_get_serial_number+ :: Ptr Word8 -> Ptr CSize+ -> X509CRLEntryPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_entry_get_expire_time+ :: Ptr Word64+ -> X509CRLEntryPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_entry_get_reason_code+ :: Ptr Word32+ -> X509CRLEntryPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_crl_entry_get_extensions+ :: Ptr X509ExtensionsPtr+ -> X509CRLEntryPtr+ -> IO BotanErrorCode
+ src/Botan/Bindings/X509/CSR.hs view
@@ -0,0 +1,45 @@+module Botan.Bindings.X509.CSR where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+-- import Botan.Bindings.MPI+import Botan.Bindings.PubKey+-- import Botan.Bindings.PubKey.Sign+import Botan.Bindings.RNG+import Botan.Bindings.X509+import Botan.Bindings.X509.Extensions+import Botan.Bindings.X509.Options++-- Certificate Signing Request, rename to that / CSR at higher levels+data X509CSRStruct+type X509CSRPtr = Ptr X509CSRStruct++foreign import ccall unsafe "&botan_x509_csr_destroy" botan_x509_csr_destroy :: FinalizerPtr X509CSRStruct++foreign import ccall unsafe botan_x509_create_cert_req+ :: Ptr X509CSRPtr+ -> X509CertOptionsPtr+ -> PrivKeyPtr+ -> Ptr CChar+ -> RNGPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_csr_create+ :: Ptr X509CSRPtr+ -> PrivKeyPtr+ -> Ptr Word8 -> CSize+ -> X509ExtensionsPtr+ -> Ptr CChar+ -> RNGPtr+ -> Ptr CChar+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_create_self_signed_cert+ :: Ptr X509CertPtr+ -> X509CertOptionsPtr+ -> PrivKeyPtr+ -> Ptr CChar+ -> RNGPtr+ -> IO BotanErrorCode+
+ src/Botan/Bindings/X509/DN.hs view
@@ -0,0 +1,56 @@+module Botan.Bindings.X509.DN where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+import Botan.Bindings.X509++data X509DNStruct+type X509DNPtr = Ptr X509DNStruct++foreign import ccall unsafe "&botan_x509_dn_destroy" botan_x509_dn_destroy :: FinalizerPtr X509DNStruct+++foreign import ccall unsafe botan_x509_dn_create+ :: Ptr X509DNPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_dn_create_from_multimap+ :: Ptr X509DNPtr+ -> Ptr Word8 -> Ptr CSize+ -> Ptr Word8 -> Ptr CSize+ -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_dn_to_string+ :: Ptr Word8 -> Ptr CSize+ -> X509DNPtr+ -> IO BotanErrorCode++-- NOTE: Returns a bool success code+foreign import ccall unsafe botan_x509_dn_has_field+ :: X509DNPtr+ -> Ptr Word8 -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_dn_get_first_attribute+ :: Ptr Word8 -> Ptr CSize+ -> X509DNPtr+ -> Ptr Word8 -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_dn_get_attribute+ :: Ptr (Ptr Word8) -> Ptr CSize -> Ptr CSize+ -> X509DNPtr+ -> Ptr Word8 -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_dn_contents+ :: Ptr (Ptr Word8) -> Ptr CSize -> Ptr (Ptr Word8) -> Ptr CSize -> Ptr CSize+ -> X509DNPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_dn_add_attribute+ :: X509DNPtr+ -> Ptr Word8 -> CSize+ -> Ptr Word8 -> CSize+ -> IO BotanErrorCode
+ src/Botan/Bindings/X509/Extensions.hs view
@@ -0,0 +1,19 @@+module Botan.Bindings.X509.Extensions where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+import Botan.Bindings.X509++data X509ExtensionStruct+type X509ExtensionPtr = Ptr X509ExtensionStruct++foreign import ccall unsafe "&botan_x509_cert_ext_destroy" botan_x509_cert_ext_destroy :: FinalizerPtr X509ExtensionStruct++data X509ExtensionsStruct+type X509ExtensionsPtr = Ptr X509ExtensionsStruct++foreign import ccall unsafe "&botan_x509_exts_destroy" botan_x509_exts_destroy :: FinalizerPtr X509ExtensionsStruct+++-- TODO: See C FFI for discussion on pending implementation+
+ src/Botan/Bindings/X509/Options.hs view
@@ -0,0 +1,152 @@+module Botan.Bindings.X509.Options where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+import Botan.Bindings.X509+import Botan.Bindings.X509.Extensions++data X509CertOptionsStruct+type X509CertOptionsPtr = Ptr X509CertOptionsStruct++foreign import ccall unsafe "&botan_x509_cert_options_destroy" botan_x509_cert_options_destroy :: FinalizerPtr X509CertOptionsStruct++foreign import ccall unsafe botan_x509_cert_options_create+ :: Ptr X509CertOptionsPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_create_common+ :: Ptr X509CertOptionsPtr+ -> Ptr CChar+ -> Ptr CChar+ -> Ptr CChar+ -> Ptr CChar+ -> Word32+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_common_name+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_country+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_organization+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_org_unit+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_more_org_units+ :: X509CertOptionsPtr+ -> Ptr (Ptr CChar) -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_locality+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_state+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_serial_number+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_email+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_uri+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_ip+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_dns+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_more_dns+ :: X509CertOptionsPtr+ -> Ptr (Ptr CChar) -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_xmpp+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_challenge+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++-- // Or _set_not_before+foreign import ccall unsafe botan_x509_cert_options_set_start+ :: X509CertOptionsPtr+ -> Word64+ -> IO BotanErrorCode++-- // Or _set_not_after+foreign import ccall unsafe botan_x509_cert_options_set_end+ :: X509CertOptionsPtr+ -> Word64+ -> IO BotanErrorCode++-- // TODO: Convenience functions for set_start_duration, set_expires++foreign import ccall unsafe botan_x509_cert_options_set_is_ca+ :: X509CertOptionsPtr+ -> CBool+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_path_limit+ :: X509CertOptionsPtr+ -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_padding_scheme+ :: X509CertOptionsPtr+ -> Ptr CChar+ -> IO BotanErrorCode++-- // Or _set_key_usage+-- // NOTE: key constraints use unsigned int in ffi, definitely need to give it something proper+foreign import ccall unsafe botan_x509_cert_options_set_key_constraints+ :: X509CertOptionsPtr+ -> CUInt+ -> IO BotanErrorCode++-- // NOTE: Technically should take OIDs but no data type for that+-- // TODO: Create list / spreadsheet of FFI data type mappings+foreign import ccall unsafe botan_x509_cert_options_set_ex_constraints+ :: X509CertOptionsPtr+ -> Ptr (Ptr CChar) -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_options_set_extensions+ :: X509CertOptionsPtr+ -> X509ExtensionsPtr+ -> IO BotanErrorCode++-- TODO: botan_x509_cert_options getters++-- TODO: botan_x509_cert_options functions (above is just members)+-- There's only a few though so its easy
+ src/Botan/Bindings/X509/Path.hs view
@@ -0,0 +1,83 @@+module Botan.Bindings.X509.Path where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+import Botan.Bindings.X509+import Botan.Bindings.X509.Store++data X509PathRestrictionsStruct+type X509PathRestrictionsPtr = Ptr X509PathRestrictionsStruct++foreign import ccall unsafe "&botan_x509_path_restrictions_destroy" botan_x509_path_restrictions_destroy :: FinalizerPtr X509PathRestrictionsStruct++foreign import ccall unsafe botan_x509_path_restrictions_create+ :: Ptr X509PathRestrictionsPtr+ -> CBool+ -> CSize+ -> CBool+ -> Word64+ -> X509CertStorePtr+ -> IO BotanErrorCode++-- TODO: botan_x509_path_restrictions_create_trusted_hashes++data X509PathValidationStruct+type X509PathValidationPtr = Ptr X509PathValidationStruct++foreign import ccall unsafe "&botan_x509_path_validation_destroy" botan_x509_path_validation_destroy :: FinalizerPtr X509PathValidationStruct++foreign import ccall unsafe botan_x509_path_validate+ :: Ptr X509PathValidationPtr+ -> X509CertPtr+ -> X509PathRestrictionsPtr+ -> X509CertStorePtr+ -> Ptr CChar+ -> CUInt -- NOTE: Assumed to be Word32+ -> Word64+ -> Word64+ -> Ptr () -- SEE NOTES ON OCSP RESPONSE - TYPE NOT YET IMPLEMENTED+ -> IO BotanErrorCode++-- // NOTE: Returns a boolean success code+foreign import ccall unsafe botan_x509_path_validation_successful_validation+ :: X509PathValidationPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_path_validation_result_string+ :: Ptr CChar -> Ptr CSize+ -> X509PathValidationPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_path_validation_trust_root+ :: Ptr X509CertPtr+ -> X509PathValidationPtr+ -> IO BotanErrorCode++-- // NOTE: Returns an array of results+-- // SEE: Discussion on arrays / ownership+-- NOTE: FFI function is actually x509_cert_t** but should be x509_cert_t* like here+foreign import ccall unsafe botan_x509_path_validation_cert_path+ :: Ptr X509CertPtr -> Ptr CSize+ -> X509PathValidationPtr+ -> IO BotanErrorCode++-- // NOTE: Botan FFI is using `int` for Certificate_Status_Code in existing code+foreign import ccall unsafe botan_x509_path_validation_status_code+ :: Ptr CInt+ -> X509PathValidationPtr+ -> IO BotanErrorCode++-- // NOTE: Returns an array of results+-- // SEE: Discussion on arrays / ownership+foreign import ccall unsafe botan_x509_path_validation_all_status_codes+ :: Ptr CInt -> Ptr CSize+ -> X509PathValidationPtr+ -> IO BotanErrorCode++-- // NOTE: Returns an array of results+-- // SEE: Discussion on arrays / ownership+-- // DOUBLE NOTE: It returns an array of cstrings+foreign import ccall unsafe botan_x509_path_validation_trusted_hashes+ :: Ptr (Ptr CChar) -> Ptr CSize -> Ptr CSize+ -> X509PathValidationPtr+ -> IO BotanErrorCode
+ src/Botan/Bindings/X509/Store.hs view
@@ -0,0 +1,188 @@+module Botan.Bindings.X509.Store where++import Botan.Bindings.Error+import Botan.Bindings.Prelude+import Botan.Bindings.PubKey+import Botan.Bindings.RNG+import Botan.Bindings.X509++data X509CertStoreStruct+type X509CertStorePtr = Ptr X509CertStoreStruct++foreign import ccall unsafe "&botan_x509_cert_store_destroy" botan_x509_cert_store_destroy :: FinalizerPtr X509CertStoreStruct++foreign import ccall unsafe botan_x509_cert_store_find_cert+ :: Ptr X509CertPtr+ -> X509CertStorePtr+ -> Ptr Word8 -> CSize+ -> Ptr Word8 -> CSize+ -> IO BotanErrorCode++-- // NOTE: Returns an array of results+-- // SEE: Discussion on arrays / ownership+-- NOTE: FFI function is actually x509_cert_t** but should be x509_cert_t* like here+foreign import ccall unsafe botan_x509_cert_store_find_all_certs+ :: Ptr X509CertPtr -> Ptr CSize+ -> X509CertStorePtr+ -> Ptr Word8 -> CSize+ -> Ptr Word8 -> CSize+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_find_cert_by_pubkey_sha1+ :: Ptr X509CertPtr+ -> X509CertStorePtr+ -> Ptr Word8 -- NOTE: SHA1 hash length is static, so we can just drop the size_t+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_find_cert_by_raw_subject_dn_sha256+ :: Ptr X509CertPtr+ -> X509CertStorePtr+ -> Ptr Word8 -- NOTE: SHA1 hash length is static, so we can just drop the size_t+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_find_crl_for+ :: Ptr X509CRLPtr+ -> X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++-- // NOTE: Returns cert_store.certificate_known ? 0 : -1;+foreign import ccall unsafe botan_x509_cert_store_certificate_known+ :: X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++{-+In-memory cert store+-}++foreign import ccall unsafe botan_x509_cert_store_in_memory_load_dir+ :: Ptr X509CertStorePtr+ -> Ptr CChar+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_in_memory_load_cert+ :: Ptr X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_in_memory_create+ :: Ptr X509CertStorePtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_in_memory_add_certificate+ :: X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_in_memory_add_crl+ :: X509CertStorePtr+ -> X509CRLPtr+ -> IO BotanErrorCode++{-+Flatfile cert store+-}++foreign import ccall unsafe botan_x509_cert_store_flatfile_create+ :: Ptr X509CertStorePtr+ -> Ptr CChar+ -> CBool+ -> IO BotanErrorCode++{-+SQL cert store+-}++-- NOTE: Returns boolean success code+foreign import ccall unsafe botan_x509_cert_store_sql_insert_cert+ :: X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++-- NOTE: Returns boolean success code+foreign import ccall unsafe botan_x509_cert_store_sql_remove_cert+ :: X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++-- NOTE: Returns nullPtr if not found+foreign import ccall unsafe botan_x509_cert_store_sql_find_key+ :: Ptr PrivKeyPtr+ -> X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++-- NOTE: See notes about returning arrays of things, improper return pointer type+foreign import ccall unsafe botan_x509_cert_store_sql_find_certs_for_key+ :: Ptr X509CertPtr -> Ptr CSize+ -> X509CertStorePtr+ -> PrivKeyPtr+ -> IO BotanErrorCode++-- NOTE: Returns boolean success code+foreign import ccall unsafe botan_x509_cert_store_sql_insert_key+ :: X509CertStorePtr+ -> X509CertPtr+ -> PrivKeyPtr+ -> IO BotanErrorCode++-- NOTE: *DOES NOT* return boolean success code+foreign import ccall unsafe botan_x509_cert_store_sql_remove_key+ :: X509CertStorePtr+ -> PrivKeyPtr+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_sql_revoke_cert+ :: X509CertStorePtr+ -> X509CertPtr+ -> Word32+ -> Word64+ -> IO BotanErrorCode++foreign import ccall unsafe botan_x509_cert_store_sql_affirm_cert+ :: X509CertStorePtr+ -> X509CertPtr+ -> IO BotanErrorCode++-- NOTE: See notes about returning arrays of things, improper return pointer type+foreign import ccall unsafe botan_x509_cert_store_sql_generate_crls+ :: Ptr X509CRLPtr -> Ptr CSize+ -> X509CertStorePtr+ -> IO BotanErrorCode++{-+SQLite3 cert store+-}++foreign import ccall unsafe botan_x509_cert_store_sqlite3_create+ :: Ptr X509CertStorePtr+ -> Ptr CChar+ -> Ptr CChar+ -> RNGPtr+ -> Ptr CChar+ -> IO BotanErrorCode++{-+System cert store+-}++foreign import ccall unsafe botan_x509_cert_store_system_create+ :: Ptr X509CertStorePtr+ -> IO BotanErrorCode++{-+MacOS cert store+-}++foreign import ccall unsafe botan_x509_cert_store_macos_create+ :: Ptr X509CertStorePtr+ -> IO BotanErrorCode++{-+Windows cert store+-}++foreign import ccall unsafe botan_x509_cert_store_windows_create+ :: Ptr X509CertStorePtr+ -> IO BotanErrorCode
+ src/Botan/Bindings/ZFEC.hs view
@@ -0,0 +1,67 @@+{-|+Module : Botan.Bindings.ZFEC+Description : ZFEC Forward Error Correction+Copyright : (c) Leo D, 2023+License : BSD-3-Clause+Maintainer : leo@apotheca.io+Stability : experimental+Portability : POSIX++The ZFEC module provides forward error correction compatible+with the zfec library.++Forward error correction takes an input and creates multiple+“shares”, such that any K of N shares is sufficient to recover+the entire original input.++Note++Specific to the ZFEC format, the first K generated shares are+identical to the original input data, followed by N-K shares of+error correcting code. This is very different from threshold+secret sharing, where having fewer than K shares gives no+information about the original input.++Warning++If a corrupted share is provided to the decoding algorithm, the+resulting decoding will be invalid. It is recommended to protect+shares using a technique such as a MAC or public key signature,+if corruption is likely in your application.++ZFEC requires that the input length be exactly divisible by K; if+needed define a padding scheme to pad your input to the necessary+size.+-}++{-# LANGUAGE CApiFFI #-}++module Botan.Bindings.ZFEC where++import Botan.Bindings.Prelude++-- | Encode some bytes with certain ZFEC parameters.+foreign import capi safe "botan/ffi.h botan_zfec_encode"+ botan_zfec_encode+ :: CSize -- ^ __K__: the number of shares needed for recovery+ -> CSize -- ^ __N__: the number of shares generated+ -> ConstPtr Word8 -- ^ __input__: the data to FEC+ -> CSize -- ^ __size__: the length in bytes of input, which must be a multiple of K+ -> Ptr (Ptr Word8) -- ^ __outputs__: An out parameter pointing to a fully allocated array of size+ -- [N][size / K]. For all n in range, an encoded block will be+ -- written to the memory starting at outputs[n][0].+ -> IO CInt -- ^ 0 on success, negative on failure++-- | Decode some previously encoded shares using certain ZFEC parameters.+foreign import capi safe "botan/ffi.h botan_zfec_decode"+ botan_zfec_decode+ :: CSize -- ^ __K__: the number of shares needed for recovery+ -> CSize -- ^ __N__: the total number of shares+ -> ConstPtr CSize -- ^ __indexes__: The index into the encoder's outputs for the corresponding+ -- element of the inputs array. Must be of length K.+ -> ConstPtr (ConstPtr Word8) -- ^ __inputs__: K previously encoded shares to decode+ -> CSize -- ^ __shareSize__: the length in bytes of each input+ -> Ptr (Ptr Word8) -- ^ __outputs__: An out parameter pointing to a fully allocated array of size+ -- [K][shareSize]. For all k in range, a decoded block will+ -- written to the memory starting at outputs[k][0].+ -> IO CInt -- ^ 0 on success, negative on failure