Skip to content

Provide helper functions to treat nonces as integers #12

Description

@redneb

Sometimes you want to use an integer as a nonce. For example, Alice might send messages to Bob using the numbers 1,3,5, ... as nonces and similarly Bob might use 2,4,6,... for the messages he sends to Alice. Another common case is to select a random nonce to encrypt the first message and then keep incrementing it for subsequent messages (sort of like a counter mode). I propose to include 2 helper functions to saltine to help with these cases:

succNonce :: Nonce -> Nonce
nonceFromInt :: Integral a => a -> Nonce

Care must be taken to make sure that those functions are implemented in an endianness independent fashion.

Here are naive implementation of the above functions, representing integers in little endian form:

succNonce :: Nonce -> Nonce
succNonce n = n'
  where
    Just n' = SC.decode $ B.pack $ succList $ B.unpack $ SC.encode n

succList :: (Bounded a, Enum a, Eq a) => [a] -> [a]
succList (x : xs)
    | x == maxBound = minBound : succList xs
    | otherwise = succ x : xs
succList [] = []

and

nonceFromInt :: Integral a => a -> Nonce
nonceFromInt x = n
  where
    Just n = SC.decode $ B.pack $ take nonceBytes $ littleEndianBytes x
    -- this is vert ugly, a #const must be used here
    nonceBytes = B.length $ SC.encode $ unsafeDupablePerformIO newNonce

littleEndianBytes :: Integral a => a -> [Word8]
littleEndianBytes x = fromIntegral r : littleEndianBytes q
  where
    (q, r) = x `quotRem` 256

where SC is Crypto.Saltine.Class and B is Data.ByteString.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions