Categorygithub.com/keybase/saltpack
modulepackage
0.0.0-20250124001807-83b98d5a6acc
Repository: https://github.com/keybase/saltpack.git
Documentation: pkg.go.dev

# README

saltpack

a modern crypto messaging format

https://saltpack.org/

Build Status GoDoc

saltpack is a streamlined, modern solution, designed with simplicity in mind. It is easy to implement & integrate. We've made few crypto decisions and instead leave almost all of the heavy lifting to the NaCl library.

saltpack is a binary message format, encoded using the MessagePack format. Messages are broken up into reasonable (1MB) chunks, over which regular NaCl operations are performed. We have taken pains to address many of the shortcomings of current message formats: (1) only authenticated data is output; (2) repudiable authentication is used wherever possible; (3) chunks cannot be reordered or combined with other transmissions; (4) the public keys of senders and recipients can be hidden; and (5) message truncation is detectable.

Visually speaking, a saltpack ASCII output looks a lot like PGP's.

saltpack

BEGIN SALTPACK SIGNED MESSAGE. kXR7VktZdyH7rvq v5wcIkHbs7XwHpb
nPtLcF6vE5yY63t aHF62jiEC1zHGqD inx5YqK0nf5W9Lp TvUmM2zBwxgd3Nw
kvzZ96W7ZfDdTVg F5Y99c2l5EsCy1I xVNl0nY1TP25vsX 2cRXXPUrM2UKtWq
UK2HG2ifBSOED4w xArcORHfFeiEZxF CqestMqLSCCE6lT HFcdvt1QX9JjmWL
o5AAqPiECnoHiSA bPHhz2JnSCyDIOz ZET1BWzttbMDL4N pcyQLmsGqYpxhG6
uvdBxdt55w9xQvQ hDPuOsKF05Hsml6 z7h9TS2msJcNwtz vxGIQR7sbB19UOt
boM1hlolmMB3loP 0KexlROFBTDC6MR nBvd9sZUxA8Z7i5 a6Dk5yFU3WEYQAo
DqqjXcp0yBoHO5O KEMqkZlyMf1PKiB 2n9wE6jwxAN1xws ccthT6X3iRYk0Br
gHW6QRXzAHLy6Ib LgY6b3UcQAoDo8b XyaExxinVuM5Ftk 75BJOWoyLGFhZS7
EfKR8jQQexvyjDM rJLxYtjvaLX7joS 2q1VcUlqGfZDhAa 4vxJQAyu57beOux
oobLhI47iZf9bxK PmYrVQ5PsC6pY1J KTQQexvlvp2yicx K4su2AFCjihbzNI
yZgKM4NHN1KZapS O3iB9SlhVfTfFcR FoQoSViTkbtDtTt 6I0jrTRHkv9XVQQ
eeeuzR7qYu1Grm3 zDPyj7JgK2mDidw HchOZnfOn59QLnM nH7ErnPRXgHuWHG
DBidjQPakJHuWsk 2ftpIyZd2NLYEFS Mqcbo6QeCdk7LA1 uobl4NXzpvi8amO
Pe8xAl1OzUCoD34 MbCwtTAe1JNymvs okufV8lHU0jVnbj u4no9QB9aP2Wkjx
PfeqIH2fEtOjmFP gPMhGWslkU0M7FL QP77gPHbgjPLSD8 yIRTrbgzpAPut5R
QhIdqVlHbUOa9sI v7gSqOi0GbUlhSM 183LxZI8pIlvgn9 Ms1WNzt5Xkv0W1Q
Qf419ZmuQVPQDOk 0hffDmUk71TlfVx XZCF3voC2ysgl3g YdLz4rDRzMJgd2m
01HIbfdsoZpAMty O27WtUNRLV1iyC9 tK5ApCyekI4nWcf 2OvTHnC8ma7bloW
XAG. END SALTPACK SIGNED MESSAGE.

PGP

-----BEGIN PGP MESSAGE-----
Comment: GPGTools - https://gpgtools.org

owEBUAKv/ZANAwAKAdIkQTsc+mSQAcsgYgBWZ0C0SSBhbSBzbyBzaWNrIG9mIHRo
aXMgc2hpdAqJAhwEAAEKAAYFAlZnQLQACgkQ0iRBOxz6ZJBS9Q/+MSfWiOz5OvRt
lHTncX8Ifo7+wSKYH039vEQAUvj+rnEdlBzcJPoHDE1yZxAZT5ek5S+cxQ5bx55K
WRLvw/sAz+OU0OPHSDsqI2LjU6D+s1EvwCISkXoWlMVx5vJsEz2XGlQ8DzgBC2Jy
wPanQf1lUz0c7k0ySdCTdZ0qG1YuaYnCXsS6g/E8E7TIO++2v5EbkgYZl3Io2LcI
C9TqTHdrIc7WGTSFjwq9JIgvwfuShpccNSFQ262gSJh8rUOzzY37q81pKxDnBvEV
TMrQYY0e/JK7KMMcHDSQSeWnMxf4/v5Qex7WI55CW4++qbNvDylDi9fTpkYfXl3B
L8pbBAxMUjcJX4qVVzWcxTwSXYO29Bi4osn2klNyZHnO35kuI9XGziWCGqhVx1MW
ptNHoVjk7/Uo7k39hY0Vjltnl/SqXHq/H7YTRSgLebuhn6zqMbmFXtyHYSHGgAQ4
rcdSBta+I9tmYCnp1GmfeXff2wzsFYPUune2Hve4VghjmeU0x7OWMEl93gpznSwu
NvzyOCqFCyfEmt/R2QCXAkxwPU/Mdsd5vzEHSMkcZgW4CTr+j5YG/C3kMy7UJAGZ
ZzFAh3/Z8fCtfREF3zH48XbNh3dQXNl40bUF/AgPvLqPf35L7TCchcUAC7oiASa/
Ph/Hao4ZzCQDM76Jr/aCUJIbxyc2zco=
=eyef
-----END PGP MESSAGE-----

The changes here are small: we've reduced our characters to base62 plus some period markers, and only at the ends of words. PGP messages often get mangled by different apps, websites, and smart text processors.

Of course, saltpack can output binary, too. Either way, it's what's inside the format that matters. You can read the spec for the details.

Post issues to: https://github.com/keybase/keybase-issues

# Packages

Package basic is a basic implementation of a saltpack key/keyring configuration.

# Functions

Armor62Open runs armor stream decoding, but on a string, and it outputs a string.
Armor62OpenWithValidation runs armor stream decoding, but on a string, and it outputs a string.
Armor62Seal takes an input plaintext and returns and output armor encoding as a string, or an error if a problem was encountered.
CheckArmor62 checks that the frame matches our standard begin/end frame.
CheckArmor62Frame checks that the frame matches our standard begin/end frame.
CheckKnownMajorVersion returns nil if the given version has a known major version.
ClassifyEncryptedStreamAndMakeDecoder takes as input an io.Reader (containing an encrypted saltpack stream), a SigncryptKeyring containing the keys to use for decryption, and a SymmetricKeyResolver (used to map an identifiers to symmetric keys in an application specific way).
ClassifyStream peeks at the beginning of a stream and checks wether it seems to contain a valid saltpack message (either armored or not).
CurrentVersion returns the Version for the currently-used Saltpack version.
Dearmor62DecryptOpen takes an armor62'ed, encrypted ciphertext and attempts to dearmor and decrypt it, using the provided keyring.
Dearmor62SigncryptOpen takes an armor62'ed, encrypted ciphertext and attempts to dearmor and decrypt it, using the provided keyring.
Dearmor62Verify checks the signature in signedMsg.
Dearmor62VerifyDetached verifies that signature is a valid armor62-encoded signature for message, and that the public key for the signer is in keyring.
Dearmor62VerifyDetachedReader verifies that signature is a valid armor62-encoded signature for entire message read from Reader, and that the public key for the signer is in keyring.
EncryptArmor62Seal is the non-streaming version of NewEncryptArmor62Stream, which inputs a plaintext (in bytes) and output a ciphertext (as a string).
IsSaltpackArmored peeks into the provided bufio.Reader to determine whether it encodes an ASCII-armored saltpack message.
IsSaltpackArmoredPrefix tries to determine whether the string is the prefix of a valid ASCII-armored saltpack message.
IsSaltpackBinary peeks into the provided bufio.Reader to determine whether it encodes a binary saltpack message.
IsSaltpackBinarySlice tries to determine if the input slice encodes the beginning of a binary saltpack message.
KnownVersions returns all known Saltpack versions.
MakeArmorFooter makes the armor footer for the message type for the given "brand".
MakeArmorHeader makes the armor header for the message type for the given "brand".
NewArmor62DecoderStream is used to decode input base62-armoring format.
NewArmor62EncoderStream makes a new Armor 62 encoding stream, using the base62-alphabet and a 32/43 encoding rate strategy.
NewDearmor62DecryptStream makes a new stream that dearmors and decrypts the given Reader stream.
NewDearmor62SigncryptOpenStream makes a new stream that dearmors and decrypts the given Reader stream.
NewDearmor62VerifyStream creates a stream that consumes data from reader r.
NewDecryptStream starts a streaming decryption.
NewEncryptArmor62Stream creates a stream that consumes plaintext data.
NewEncryptStream creates a stream that consumes plaintext data.
NewSignArmor62Stream creates a stream that consumes plaintext data.
NewSigncryptArmor62SealStream creates a stream that consumes plaintext data.
NewSigncryptOpenStream starts a streaming verification and decryption.
NewSigncryptSealStream creates a stream that consumes plaintext data.
NewSignDetachedArmor62Stream creates a stream that consumes plaintext data.
NewSignDetachedStream creates a stream that consumes plaintext data.
NewSignStream creates a stream that consumes plaintext data.
NewVerifyStream creates a stream that consumes data from reader r.
Open simply opens a ciphertext given the set of keys in the specified keyring.
PublicKeyEqual returns true if the two public keys are equal.
Seal a plaintext from the given sender, for the specified receiver groups.
Sign creates an attached signature message of plaintext from signer.
SignArmor62 creates an attached armored signature message of plaintext from signer.
SigncryptArmor62Seal is the non-streaming version of NewSigncryptArmor62SealStream, which inputs a plaintext (in bytes) and output a ciphertext (as a string).
SigncryptOpen simply opens a ciphertext given the set of keys in the specified keyring.
SigncryptSeal a plaintext from the given sender, for the specified receiver groups.
SignDetached returns a detached signature of plaintext from signer.
SignDetachedArmor62 returns a detached armored signature of plaintext from signer.
SingleVersionValidator returns a VersionValidator that returns nil if its given version is equal to desiredVersion.
Verify checks the signature in signedMsg.
VerifyDetached verifies that signature is a valid signature for message, and that the public key for the signer is in keyring.
VerifyDetachedReader verifies that signature is a valid signature for entire message read from message Reader, and that the public key for the signer is in keyring.
Version1 returns the Version for Saltpack V1.
Version2 returns the Version for Saltpack V2.

# Constants

DetachedSignatureArmorString is included in armor headers for detached signatures.
EncryptionArmorString is included in armor headers for encrypted messages.
FormatName is the publicly advertised name of the format, used in the header of the message and also in Nonce creation.
MessageTypeAttachedSignature is a packet type to describe an attached signature.
MessageTypeDetachedSignature is a packet type to describe a detached signature.
MessageTypeEncryption is a packet type to describe an encryption message.
MessageTypeSigncryption is a packet type to describe a signcrypted message.
MessageTypeUnknown is used by the decoding functions to indicate an unknown message type or a decoding error.
SignedArmorString is included in armor headers for signed messages.

# Variables

Armor62Params are the armoring parameters we recommend for use with a generic armorer.
ErrBadBoxKey is returned if a key with the wrong number of bytes is discovered in the encryption header.
ErrBadEphemeralKey is for when an ephemeral key fails to be properly imported.
ErrBadLookup is when the user-provided key lookup gives a bad value.
ErrBadReceivers shows up when you pass a bad receivers vector.
ErrBadSenderKeySecretbox is returned if the sender secretbox fails to open.
ErrBadSignature is returned when verification of a block fails.
ErrBadSymmetricKey is returned if a key with the wrong number of bytes is discovered in the encryption header.
ErrDecryptionFailed is returned when a decryption fails.
ErrFailedToReadHeaderBytes indicates that we failed to read the doubly-encoded header bytes object from the input stream.
ErrInsufficientRandomness is generated when the encryption fails to collect enough randomness to proceed.
ErrNoDecryptionKey is an error indicating no decryption key was found for the incoming message.
ErrNotASaltpackMessage is returned when the message given as input is not a valid saltpack message.
ErrOverflow is returned if we were looking for punctuation but our quota was overflowed before we found the needed character.
ErrPacketOverflow indicates that more than (2^64-2) packets were found in an encryption stream.
ErrPunctuated is produced when a punctuation character is found in the stream.
ErrShortSliceOrBuffer is returned when the input slice or buffer provided is too short to determine if it is the beginning of a binary saltpack message.
ErrTrailingGarbage indicates that additional msgpack packets were found after the end of the encryption stream.
ErrUnexpectedEmptyBlock is returned when an empty block is encountered that isn't both the last one and the first one (for V2 and higher), or isn't the last one (for V1).
ErrWrongNumberOfKeys is returned when the resolved list of keys isn't the same length as the identifiers list.

# Structs

EncryptionHeader is the first packet in an encrypted message.
ErrBadFrame shows up when the BEGIN or END frames have issues.
ErrBadVersion is returned if a packet of an unsupported version is found.
ErrInvalidParameter signifies that a function was called with an invalid parameter.
ErrNoSenderKey indicates that on decryption/verification we couldn't find a public key for the sender.
ErrWrongMessageType is produced if one packet tag was expected, but a packet of another tag was found.
MessageKeyInfo conveys all of the data about the keys used in this encrypted message.
ReceiverSymmetricKey is a symmetric key paired with an identifier.
SignatureHeader is the first packet in a signed message.
Version is a major.minor pair that shows the version of the whole file.

# Interfaces

BasePublicKey types can output a key ID corresponding to the key.
BoxPrecomputedSharedKey results from a Precomputation below.
BoxPublicKey is an generic interface to NaCl's public key Box function.
BoxSecretKey is the secret key corresponding to a BoxPublicKey.
EphemeralKeyCreator is an interface for objects that can create random ephemeral keys.
Frame is a way to read the frame out of a Decoder stream.
Keyring is an interface used with decryption; it is called to recover public or private keys during the decryption process.
SigKeyring is an interface used during verification to find the public key for the signer of a message.
SigncryptKeyring is a combination of the Keyring and SigKeyring interfaces.
SigningPublicKey is a public NaCl key that can verify signatures.
SigningSecretKey is a secret NaCl key that can sign messages.
SymmetricKeyResolver is an interface for resolving identifiers to keys.

# Type aliases

ErrBadCiphertext is generated when decryption fails due to improper authentication.
ErrBadTag is generated when a payload hash doesn't match the hash authenticator.
ErrRepeatedKey is produced during encryption if a key is repeated; keys must be unique.
FrameChecker is a function intended to check the frame of the armor is valid.
HeaderChecker is a function intended to check that an header (the initial part of an armor before and not including the first punctuation) is valid.
MessageType is an int used to describe what "type" of message it is.
Nonce is a NaCl-style nonce, with 24 bytes of data, some of which can be counter values, and some of which can be random-ish values.
RawBoxKey is the raw byte-representation of what a box key should look like, a static 32-byte buffer.
The SigncryptionHeader has exactly the same structure as the EncryptionHeader, though the byte slices represent different types of keys.
SymmetricKey is a template for a symmetric key, a 32-byte static buffer.
VersionValidator is a function that takes a version and returns nil if it's a valid version, and an error otherwise.