Use edown for documentation.

parent 5f2600fb
SPHINCS-256 NIF for Erlang
===========================
[![Build Status](https://travis-ci.org/ahf/sphincs.svg?branch=develop)](https://travis-ci.org/ahf/sphincs)
SPHINCS-256 is a high-security post-quantum stateless hash-based signature
scheme. This repository contains the SPHINCS-256 implementation found in the
SUPERCOP performance suite together with an Erlang NIF's for the SPHINCS API.
SPHINCS-256 uses 41 KB signatures, 1 KB public keys, and 1 KB private keys.
For more information about SPHINCS see:
- http://sphincs.cr.yp.to
- http://bench.cr.yp.to/supercop.html
## Usage
1. Create a keypair.
1> #{ secret := Secret, public := Public } = sphincs:keypair().
#{public => <<188,75,148,147,203,240,152,149,40,103,197,233,4,199,
245,227,31,251,245,128,2,168,21,194,235,35,151,252,...>>,
secret => <<190,137,81,29,80,110,124,82,179,203,5,180,19,120,3,111,
79,205,116,240,52,112,78,227,78,142,140,...>>}
2. Sign a document.
2> SignedDocument = sphincs:sign(<<"Hello world!">>, Secret).
<<169,24,140,16,104,204,246,11,124,204,196,91,67,108,125,
104,108,77,153,127,231,174,138,213,44,62,250,130,253,...>>
3. Verify a signed document.
3> sphincs:verify(SignedDocument, Public).
{ok,<<"Hello world!">>}
## Current Issues
- It's currently only the `ref` implementation of BLAKE-256, BLAKE-512, ChaCha12
and SPHINCS-256 that have been tested. It would be nice to have vectorized
versions for higher performance.
- More tests :-)
# SPHINCS-256 NIF for Erlang #
__Version:__ 1.0.0 (SUPERCOP: 20141124)
__Authors:__ Alexander Færøy ([`ahf@0x90.dk`](mailto:ahf@0x90.dk)).
SPHINCS-256 is a high-security post-quantum stateless hash-based signature
scheme. This repository contains the SPHINCS-256 implementation found in the
SUPERCOP performance suite together with an Erlang NIF's for the SPHINCS API.
SPHINCS-256 uses 41 KB signatures, 1 KB public keys, and 1 KB private keys.
For more information about SPHINCS see:
- [sphincs.cr.yp.to](http://sphincs.cr.yp.to/)
- [supercop](http://bench.cr.yp.to/supercop.md)
### <a name="Example_Usage">Example Usage</a> ###
1. Alice generates a new keypair and sends her public key to Bob.
```erlang
#{ secret := Secret, public := Public } = sphincs:keypair().
```
2. Alice signs a document and sends it to Bob.
```erlang
SignedDocument = sphincs:sign(Message, Secret).
```
3. Bob verifies the signed document from Alice.
```erlang
sphincs:verify(SignedDocument, Public).
```
### <a name="Issues">Issues</a> ###
- It's currently only the `ref` implementation of BLAKE-256,
BLAKE-512, ChaCha12 and SPHINCS-256 that have been tested. It would be nice
to have vectorized versions for higher performance.
- The Erlang bindings of sphincs could use some tests :-)
## Modules ##
<table width="100%" border="0" summary="list of modules">
<tr><td><a href="https://lab.baconsvin.org/ahf/sphincs/blob/develop/doc/sphincs.md" class="module">sphincs</a></td></tr></table>
# SPHINCS-256 NIF for Erlang #
__Version:__ 1.0.0 (SUPERCOP: 20141124)
__Authors:__ Alexander Færøy ([`ahf@0x90.dk`](mailto:ahf@0x90.dk)).
SPHINCS-256 is a high-security post-quantum stateless hash-based signature
scheme. This repository contains the SPHINCS-256 implementation found in the
SUPERCOP performance suite together with an Erlang NIF's for the SPHINCS API.
SPHINCS-256 uses 41 KB signatures, 1 KB public keys, and 1 KB private keys.
For more information about SPHINCS see:
- [sphincs.cr.yp.to](http://sphincs.cr.yp.to/)
- [supercop](http://bench.cr.yp.to/supercop.md)
### <a name="Example_Usage">Example Usage</a> ###
1. Alice generates a new keypair and sends her public key to Bob.
```erlang
#{ secret := Secret, public := Public } = sphincs:keypair().
```
2. Alice signs a document and sends it to Bob.
```erlang
SignedDocument = sphincs:sign(Message, Secret).
```
3. Bob verifies the signed document from Alice.
```erlang
sphincs:verify(SignedDocument, Public).
```
### <a name="Issues">Issues</a> ###
- It's currently only the `ref` implementation of BLAKE-256,
BLAKE-512, ChaCha12 and SPHINCS-256 that have been tested. It would be nice
to have vectorized versions for higher performance.
- The Erlang bindings of sphincs could use some tests :-)
## Modules ##
<table width="100%" border="0" summary="list of modules">
<tr><td><a href="sphincs.md" class="module">sphincs</a></td></tr></table>
%% encoding: UTF-8
{application,sphincs}.
{modules,[sphincs]}.
@title SPHINCS-256 NIF for Erlang
@version 1.0.0 (SUPERCOP: 20141124)
@author Alexander Færøy <ahf@0x90.dk>
@doc
SPHINCS-256 is a high-security post-quantum stateless hash-based signature
scheme. This repository contains the SPHINCS-256 implementation found in the
SUPERCOP performance suite together with an Erlang NIF's for the SPHINCS API.
SPHINCS-256 uses 41 KB signatures, 1 KB public keys, and 1 KB private keys.
For more information about SPHINCS see:
- <a href="http://sphincs.cr.yp.to/">sphincs.cr.yp.to</a>
- <a href="http://bench.cr.yp.to/supercop.html">supercop</a>
== Example Usage ==
1. Alice generates a new keypair and sends her public key to Bob.
<pre lang="erlang">#{ secret := Secret, public := Public } = sphincs:keypair().</pre>
2. Alice signs a document and sends it to Bob.
<pre lang="erlang">SignedDocument = sphincs:sign(Message, Secret).</pre>
3. Bob verifies the signed document from Alice.
<pre lang="erlang">sphincs:verify(SignedDocument, Public).</pre>
== Issues ==
- It's currently only the <code>ref</code> implementation of BLAKE-256,
BLAKE-512, ChaCha12 and SPHINCS-256 that have been tested. It would be nice
to have vectorized versions for higher performance.
- The Erlang bindings of sphincs could use some tests :-)
@end
# Module sphincs #
* [Description](#description)
* [Data Types](#types)
* [Function Index](#index)
* [Function Details](#functions)
SPHINCS-256 NIF for Erlang.
__Authors:__ Alexander Færøy ([`ahf@0x90.dk`](mailto:ahf@0x90.dk)).
<a name="types"></a>
## Data Types ##
### <a name="type-keypair">keypair()</a> ###
<pre><code>
keypair() = #{secret =&gt; <a href="#type-secret_key">secret_key()</a>, public =&gt; <a href="#type-public_key">public_key()</a>}
</code></pre>
### <a name="type-public_key">public_key()</a> ###
<pre><code>
public_key() = binary()
</code></pre>
### <a name="type-secret_key">secret_key()</a> ###
<pre><code>
secret_key() = binary()
</code></pre>
<a name="index"></a>
## Function Index ##
<table width="100%" border="1" cellspacing="0" cellpadding="2" summary="function index"><tr><td valign="top"><a href="#keypair-0">keypair/0</a></td><td>Generate a new SPHINCS-256 keypair.</td></tr><tr><td valign="top"><a href="#sign-2">sign/2</a></td><td>Sign a message using a SPHINCS-256 secret key.</td></tr><tr><td valign="top"><a href="#verify-2">verify/2</a></td><td>Verify a given signed message using a SPHINCS-256 public key.</td></tr></table>
<a name="functions"></a>
## Function Details ##
<a name="keypair-0"></a>
### keypair/0 ###
<pre><code>
keypair() -&gt; {ok, KeyPair} | {error, Reason}
</code></pre>
<ul class="definitions"><li><code>KeyPair = <a href="#type-keypair">keypair()</a></code></li><li><code>Reason = term()</code></li></ul>
Generate a new SPHINCS-256 keypair.
Generates and returns a new SPHINCS-256 keypair. The return value is a map
in order to ensure that the public key is not used as a secret key and vice
versa.
<a name="sign-2"></a>
### sign/2 ###
<pre><code>
sign(Message, SecretKey) -&gt; SignedMessage
</code></pre>
<ul class="definitions"><li><code>Message = iolist()</code></li><li><code>SecretKey = <a href="#type-secret_key">secret_key()</a></code></li><li><code>SignedMessage = binary()</code></li></ul>
Sign a message using a SPHINCS-256 secret key.
Sign a given message with a SPHINCS-256 secret key. The return value is a
binary containing the signature followed by the message itself.
<a name="verify-2"></a>
### verify/2 ###
<pre><code>
verify(SignedMessage, PublicKey) -&gt; {ok, Message} | {error, Reason}
</code></pre>
<ul class="definitions"><li><code>SignedMessage = iolist()</code></li><li><code>PublicKey = <a href="#type-public_key">public_key()</a></code></li><li><code>Message = binary()</code></li><li><code>Reason = term()</code></li></ul>
Verify a given signed message using a SPHINCS-256 public key.
Verify a given message with a SPHINCS-256 public key. The return value
contains the message itself with the signature stripped if the verification
was succesful, otherwise an error tuple is returned.
......@@ -47,7 +47,7 @@
{edoc_opts, [
{doclet, edown_doclet},
{top_level_readme, {"./README.md", "https://lab.baconsvin.org/ahf/luke"}},
{top_level_readme, {"./README.md", "https://lab.baconsvin.org/ahf/sphincs"}},
{todo, true},
{report_missing_types, true},
{source_path, ["src"]},
......
%%%
%%% Copyright (c) 2016 Alexander Færøy. All rights reserved.
%%% Use of this source code is governed by a BSD-style
%%% license that can be found in the LICENSE file.
%%%
%%% -----------------------------------------------------------
%%% @author Alexander Færøy <ahf@0x90.dk>
%%% @doc SPHINCS-256 NIF for Erlang
%%% @end
%%% -----------------------------------------------------------
-module(sphincs).
%% API.
......@@ -5,30 +15,65 @@
sign/2,
verify/2]).
-ifdef(TEST).
-include_lib("triq/include/triq.hrl").
-endif.
%% Types.
-export_type([secret_key/0,
public_key/0,
keypair/0
]).
-type secret_key() :: binary().
-type public_key() :: binary().
-type keypair() :: #{ secret => secret_key(), public => public_key() }.
-spec keypair() -> keypair().
%% @doc Generate a new SPHINCS-256 keypair.
%%
%% Generates and returns a new SPHINCS-256 keypair. The return value is a map
%% in order to ensure that the public key is not used as a secret key and vice
%% versa.
%%
%% @end
-spec keypair() -> {ok, KeyPair} | {error, Reason}
when
KeyPair :: keypair(),
Reason :: term().
keypair() ->
case sphincs_nif:keypair(crypto:strong_rand_bytes(1088)) of
{error, _} = Error ->
Error;
{Public, Secret} ->
#{ public => Public, secret => Secret }
{ok, #{ public => Public,
secret => Secret }}
end.
-spec sign(Message :: binary(), Secret :: secret_key()) -> binary().
%% @doc Sign a message using a SPHINCS-256 secret key.
%%
%% Sign a given message with a SPHINCS-256 secret key. The return value is a
%% binary containing the signature followed by the message itself.
%%
%% @end
-spec sign(Message, SecretKey) -> SignedMessage
when
Message :: iolist(),
SecretKey :: secret_key(),
SignedMessage :: binary().
sign(Message, Secret) when is_binary(Message), is_binary(Secret) ->
sphincs_nif:sign(Message, Secret).
-spec verify(Message :: binary(), Public :: public_key()) -> {ok, binary()} | {error, term()}.
%% @doc Verify a given signed message using a SPHINCS-256 public key.
%%
%% Verify a given message with a SPHINCS-256 public key. The return value
%% contains the message itself with the signature stripped if the verification
%% was succesful, otherwise an error tuple is returned.
%%
%% @end
-spec verify(SignedMessage, PublicKey) -> {ok, Message} | {error, Reason}
when
SignedMessage :: iolist(),
PublicKey :: public_key(),
Message :: binary(),
Reason :: term().
verify(SignedMessage, Public) when is_binary(SignedMessage), is_binary(Public) ->
case sphincs_nif:verify(SignedMessage, Public) of
Message when is_binary(Message) ->
......@@ -37,17 +82,3 @@ verify(SignedMessage, Public) when is_binary(SignedMessage), is_binary(Public) -
{error, _} = Error ->
Error
end.
-ifdef(TEST).
key() ->
#{ secret := Secret, public := Public } = keypair(),
{Public, Secret}.
prop_create_sign_verify_valid() ->
?FORALL({{Public, Secret}, Message}, {key(), binary()},
begin
SignedMessage = sign(Message, Secret),
{ok, VerifiedMessage} = verify(SignedMessage, Public),
Message =:= VerifiedMessage
end).
-endif.
%%%
%%% Copyright (c) 2016 Alexander Færøy. All rights reserved.
%%% Use of this source code is governed by a BSD-style
%%% license that can be found in the LICENSE file.
%%%
%%% ----------------------------------------------------------------------------
%%% @author Alexander Færøy <ahf@0x90.dk>
%%% @private
%%% ----------------------------------------------------------------------------
-module(sphincs_nif).
%% Private API.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment