SWITCH from v01 to v03

Versions are incompatible due to different address formats and differing message compression!
This commit is contained in:
Andreas 2016-02-16 16:31:18 +01:00
parent 59a4846fbd
commit c37b9dcfca
15 changed files with 230 additions and 201 deletions

View File

@ -11,19 +11,19 @@ test/test_xmssmt
test/test_chacha: chacha.c prg.c randombytes.c test/test_chacha.c chacha.h prg.h randombytes.h
$(CC) $(CFLAGS) chacha.c prg.c randombytes.c test/test_chacha.c -o $@ -lcrypto -lm
test/test_wots: chacha.c hash.c prg.c randombytes.c wots.c xmss_commons.c test/test_wots.c chacha.h hash.h prg.h randombytes.h wots.h xmss_commons.h
test/test_wots: chacha.c hash.c prg.c randombytes.c wots.c xmss_commons.c test/test_wots.c chacha.h hash.h hash_address.h prg.h randombytes.h wots.h xmss_commons.h
$(CC) $(CFLAGS) chacha.c hash.c prg.c randombytes.c wots.c xmss_commons.c test/test_wots.c -o $@ -lcrypto -lm
test/test_xmss: chacha.c hash.c prg.c randombytes.c wots.c xmss.c xmss_commons.c test/test_xmss.c chacha.h hash.h prg.h randombytes.h wots.h xmss.h xmss_commons.h
test/test_xmss: chacha.c hash.c prg.c randombytes.c wots.c xmss.c xmss_commons.c test/test_xmss.c chacha.h hash.h hash_address.h prg.h randombytes.h wots.h xmss.h xmss_commons.h
$(CC) $(CFLAGS) chacha.c hash.c prg.c randombytes.c wots.c xmss.c xmss_commons.c test/test_xmss.c -o $@ -lcrypto -lm
test/test_xmss_fast: chacha.c hash.c prg.c randombytes.c wots.c xmss_fast.c xmss_commons.c test/test_xmss_fast.c chacha.h hash.h prg.h randombytes.h wots.h xmss_fast.h xmss_commons.h
test/test_xmss_fast: chacha.c hash.c prg.c randombytes.c wots.c xmss_fast.c xmss_commons.c test/test_xmss_fast.c chacha.h hash.h hash_address.h prg.h randombytes.h wots.h xmss_fast.h xmss_commons.h
$(CC) $(CFLAGS) chacha.c hash.c prg.c randombytes.c wots.c xmss_fast.c xmss_commons.c test/test_xmss_fast.c -o $@ -lcrypto -lm
test/test_xmssmt: chacha.c hash.c prg.c randombytes.c wots.c xmss.c xmss_commons.c test/test_xmssmt.c chacha.h hash.h prg.h randombytes.h wots.h xmss.h xmss_commons.h
test/test_xmssmt: chacha.c hash.c prg.c randombytes.c wots.c xmss.c xmss_commons.c test/test_xmssmt.c chacha.h hash.h hash_address.h prg.h randombytes.h wots.h xmss.h xmss_commons.h
$(CC) $(CFLAGS) chacha.c hash.c prg.c randombytes.c wots.c xmss.c xmss_commons.c test/test_xmssmt.c -o $@ -lcrypto -lm
test/test_xmssmt_fast: chacha.c hash.c prg.c randombytes.c wots.c xmss_fast.c xmss_commons.c test/test_xmssmt_fast.c chacha.h hash.h prg.h randombytes.h wots.h xmss_fast.h xmss_commons.h
test/test_xmssmt_fast: chacha.c hash.c prg.c randombytes.c wots.c xmss_fast.c xmss_commons.c test/test_xmssmt_fast.c chacha.h hash.h hash_address.h prg.h randombytes.h wots.h xmss_fast.h xmss_commons.h
$(CC) $(CFLAGS) chacha.c hash.c prg.c randombytes.c wots.c xmss_fast.c xmss_commons.c test/test_xmssmt_fast.c -o $@ -lcrypto -lm
.PHONY: clean

28
hash.c
View File

@ -1,10 +1,12 @@
/*
hash.c version 20151120
hash.c version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/
#include "prg.h"
#include "hash_address.h"
#include <stddef.h>
#include <stdio.h>
@ -14,12 +16,6 @@ Public domain.
#include <openssl/evp.h>
#define SET_KEY_BIT(a, b) (a[15] = (a[15] & 253) | ((b << 1) & 2))
#define SET_BLOCK_BIT(a, b) (a[15] = (a[15] & 254) | (b & 1))
#define WOTS_SELECT_KEY(a) (a[15] = (a[15] & 254) | 1)
#define WOTS_SELECT_BLOCK(a) (a[15] = (a[15] & 254) | 0)
/**
* Implements PRF_m
*/
@ -51,29 +47,27 @@ int prf_m(unsigned char *out, const unsigned char *in, size_t inlen, const unsig
int hash_m(unsigned char *out, const unsigned char *in, unsigned long long inlen, const unsigned char *key, const unsigned int keylen, const unsigned int m)
{
unsigned int i;
unsigned char buf[inlen + keylen + m];
unsigned char buf[inlen + keylen];
if (keylen != m){
fprintf(stderr, "H_m takes m-bit keys, we got m=%d but a keylength of %d.\n", m, keylen);
if (keylen != 2*m){
fprintf(stderr, "H_m takes 2m-bit keys, we got m=%d but a keylength of %d.\n", m, keylen);
return 1;
}
for (i=0; i < m; i++) {
buf[i] = 0x00;
}
for (i=0; i < keylen; i++) {
buf[m + i] = key[i];
buf[i] = key[i];
}
for (i=0; i < inlen; i++) {
buf[m + keylen + i] = in[i];
buf[keylen + i] = in[i];
}
if (m == 32) {
SHA256(buf, inlen + keylen + m, out);
SHA256(buf, inlen + keylen, out);
return 0;
}
else {
if (m == 64) {
SHA512(buf, inlen + keylen + m, out);
SHA512(buf, inlen + keylen, out);
return 0;
}
}

3
hash.h
View File

@ -1,6 +1,7 @@
/*
hash.h version 20151120
hash.h version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/

83
hash_address.h Normal file
View File

@ -0,0 +1,83 @@
/*
hash.c version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/
/*
* Used in hash.c
*/
#define SET_BLOCK_BIT(a, b) (a[15] = (a[15] & 1) | ((b << 1) & 2))
#define SET_KEY_BIT(a, b) (a[15] = (a[15] & 2) | (b & 1))
#define WOTS_SELECT_KEY(a) (a[15] = 1)
#define WOTS_SELECT_BLOCK(a) (a[15] = 0)
/*
* Used in wots.c
*/
#define SET_HASH_ADDRESS(a, v) {\
a[14] = (v & 255);}
#define SET_CHAIN_ADDRESS(a, v) {\
a[13] = (v & 255);\
a[12] = ((v >> 8) & 255);}
/*
* Used in xmss_fast.c and xmss.c
*/
#define SET_LAYER_ADDRESS(a, v) {\
a[0] = (v & 255);}
#define SET_TREE_ADDRESS(a, v) {\
a[5] = (v & 255);\
a[4] = (v >> 8) & 255;\
a[3] = (v >> 16) & 255;\
a[2] = (v >> 24) & 255;\
a[1] = (v >> 32) & 255;}
#define SET_OTS_BIT(a, b) {\
a[6] = (b & 1);\
a[7] = 0;\
a[8] = 0;}
#define SET_OTS_ADDRESS(a, v) {\
a[11] = (v & 255);\
a[10] = (v >> 8) & 255;\
a[9] = (v >> 16) & 255;}
#define ZEROISE_OTS_ADDR(a) {\
a[12] = 0;\
a[13] = 0;\
a[14] = 0;\
a[15] = 0;}
#define SET_LTREE_BIT(a, b) {\
a[7] = (a[7] & 0) | (b & 1);}
#define SET_LTREE_ADDRESS(a, v) {\
a[10] = v & 255;\
a[9] = (v >> 8) & 255;\
a[8] = (v >> 16) & 255;}
#define SET_LTREE_TREE_HEIGHT(a, v) {\
a[11] = (v & 255);}
#define SET_LTREE_TREE_INDEX(a, v) {\
a[14] = (v & 255);\
a[13] = (v >> 8) & 255;\
a[12] = (v >> 16) & 3;}
#define SET_NODE_PADDING(a) {\
a[8] = 0;\
a[9] = 0;\
a[10] = 0;}
#define SET_NODE_TREE_HEIGHT(a, v) {\
a[11] = (v & 255);}
#define SET_NODE_TREE_INDEX(a, v) {\
a[14] = v & 255;\
a[13] = (v >> 8) & 255;\
a[12] = (v >> 16) & 255;}

3
prg.c
View File

@ -1,6 +1,7 @@
/*
prg.c version 20151120
prg.c version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/
#include "chacha.h"

3
prg.h
View File

@ -1,6 +1,7 @@
/*
prg.h version 20151120
prg.h version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/

View File

@ -14,8 +14,8 @@ int main()
{
int r;
unsigned long long i;
unsigned int m = 64;
unsigned int n = 64;
unsigned int m = 32;
unsigned int n = 32;
unsigned int h = 8;
unsigned int w = 16;

17
wots.c
View File

@ -1,6 +1,7 @@
/*
wots.c version 20151120
wots.c version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/
@ -11,19 +12,7 @@ Public domain.
#include "prg.h"
#include "hash.h"
#include "wots.h"
/**
* Macros used to manipulate the respective fields
* in the 16byte hash address
*/
#define SET_HASH_ADDRESS(a, v) {\
a[15] = (a[15] & 1) | ((v << 1) & 254);\
a[14] = (a[14] & 254) | ((v >> 7) & 1);}
#define SET_CHAIN_ADDRESS(a, v) {\
a[14] = (a[14] & 1) | ((v << 1) & 254);\
a[13] = (v >> 7) & 255;\
a[12] = (a[12] & 254) | ((v >> 15) & 1);}
#include "hash_address.h"
void wots_set_params(wots_params *params, int m, int n, int w)

3
wots.h
View File

@ -1,6 +1,7 @@
/*
wots.h version 20151120
wots.h version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/

130
xmss.c
View File

@ -1,6 +1,7 @@
/*
xmss.c version 20151120
xmss.c version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/
@ -15,69 +16,11 @@ Public domain.
#include "hash.h"
#include "prg.h"
#include "xmss_commons.h"
#include "hash_address.h"
// For testing
#include "stdio.h"
/**
* Macros used to manipulate the respective fields
* in the 16byte hash address
*/
#define SET_LAYER_ADDRESS(a, v) {\
a[6] = (a[6] & 3) | ((v << 2) & 252);\
a[5] = (a[5] & 252) | ((v >> 6) & 3);}
#define SET_TREE_ADDRESS(a, v) {\
a[9] = (a[9] & 3) | ((v << 2) & 252);\
a[8] = (v >> 6) & 255;\
a[7] = (v >> 14) & 255;\
a[6] = (a[6] & 252) | ((v >> 22) & 3);}
#define SET_OTS_BIT(a, b) {\
a[9] = (a[9] & 253) | ((b << 1) & 2);}
#define SET_OTS_ADDRESS(a, v) {\
a[12] = (a[12] & 1) | ((v << 1) & 254);\
a[11] = (v >> 7) & 255;\
a[10] = (v >> 15) & 255;\
a[9] = (a[9] & 254) | ((v >> 23) & 1);}
#define ZEROISE_OTS_ADDR(a) {\
a[12] = (a[12] & 254);\
a[13] = 0;\
a[14] = 0;\
a[15] = 0;}
#define SET_LTREE_BIT(a, b) {\
a[9] = (a[9] & 254) | (b & 1);}
#define SET_LTREE_ADDRESS(a, v) {\
a[12] = v & 255;\
a[11] = (v >> 8) & 255;\
a[10] = (v >> 16) & 255;}
#define SET_LTREE_TREE_HEIGHT(a, v) {\
a[13] = (a[13] & 3) | ((v << 2) & 252);}
#define SET_LTREE_TREE_INDEX(a, v) {\
a[15] = (a[15] & 3) | ((v << 2) & 252);\
a[14] = (v >> 6) & 255;\
a[13] = (a[13] & 252) | ((v >> 14) & 3);}
#define SET_NODE_PADDING(a) {\
a[10] = 0;\
a[11] = a[11] & 3;}
#define SET_NODE_TREE_HEIGHT(a, v) {\
a[12] = (a[12] & 3) | ((v << 2) & 252);\
a[11] = (a[11] & 252) | ((v >> 6) & 3);}
#define SET_NODE_TREE_INDEX(a, v) {\
a[15] = (a[15] & 3) | ((v << 2) & 252);\
a[14] = (v >> 6) & 255;\
a[13] = (v >> 14) & 255;\
a[12] = (a[12] & 252) | ((v >> 22) & 3);}
/**
* Used for pseudorandom keygeneration,
@ -382,7 +325,16 @@ int xmss_sign(unsigned char *sk, unsigned char *sig_msg, unsigned long long *sig
memcpy(sk_prf, sk+4+n, m);
unsigned char pub_seed[n];
memcpy(pub_seed, sk+4+n+m, n);
unsigned char hash_key[2*m];
unsigned long long i;
for(i = 0; i < m-4; i++){
hash_key[i] = 0;
}
for(i = 0; i < 4; i++){
hash_key[i+m-4] = sk[i];
}
// Update SK
sk[0] = ((idx + 1) >> 24) & 255;
sk[1] = ((idx + 1) >> 16) & 255;
@ -392,7 +344,6 @@ int xmss_sign(unsigned char *sk, unsigned char *sig_msg, unsigned long long *sig
// -- A productive implementation should use a file handle instead and write the updated secret key at this point!
// Init working params
unsigned long long i;
unsigned char R[m];
unsigned char msg_h[m];
unsigned char root[n];
@ -404,10 +355,12 @@ int xmss_sign(unsigned char *sk, unsigned char *sig_msg, unsigned long long *sig
// ---------------------------------
// Message Hash:
// First compute pseudorandom key
// First compute pseudorandom value
prf_m(R, msg, msglen, sk_prf, m);
// Generate hash key (idx || R)
memcpy(hash_key+m, R, m);
// Then use it for message digest
hash_m(msg_h, msg, msglen, R, m, m);
hash_m(msg_h, msg, msglen, hash_key, 2*m, m);
// Start collecting signature
*sig_msg_len = 0;
@ -472,6 +425,7 @@ int xmss_sign_open(unsigned char *msg, unsigned long long *msglen, const unsigne
unsigned char pkhash[n];
unsigned char root[n];
unsigned char msg_h[m];
unsigned char hash_key[2*m];
unsigned char pub_seed[n];
memcpy(pub_seed, pk+n, n);
@ -494,16 +448,19 @@ int xmss_sign_open(unsigned char *msg, unsigned long long *msglen, const unsigne
// Extract index
idx = ((unsigned long)sig_msg[0] << 24) | ((unsigned long)sig_msg[1] << 16) | ((unsigned long)sig_msg[2] << 8) | sig_msg[3];
printf("verify:: idx = %lu\n", idx);
sig_msg += 4;
sig_msg_len -= 4;
for(i = 0; i < m-4; i++){
hash_key[i] = 0;
}
for(i = 0; i < m+4; i++){
hash_key[i+m-4] = sig_msg[i];
}
sig_msg += (m+4);
sig_msg_len -= (m+4);
// hash message (recall, R is now on pole position at sig_msg
unsigned long long tmp_sig_len = m+params->wots_par.keysize+params->h*n;
// hash message
unsigned long long tmp_sig_len = params->wots_par.keysize+params->h*n;
m_len = sig_msg_len - tmp_sig_len;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, sig_msg, m, m);
sig_msg += m;
sig_msg_len -= m;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, hash_key, 2*m, m);
//-----------------------
// Verify signature
@ -596,15 +553,20 @@ int xmssmt_sign(unsigned char *sk, unsigned char *sig_msg, unsigned long long *s
unsigned char pub_seed[n];
// Init working params
unsigned char R[m];
unsigned char hash_key[2*m];
unsigned char msg_h[m];
unsigned char root[n];
unsigned char ots_seed[n];
unsigned char ots_addr[16] = {0, 0, 0, 0};
// Extract SK
for(i = 0; i < m-idx_len; i++){
hash_key[i] = 0;
}
unsigned long long idx = 0;
for (i = 0; i < idx_len; i++) {
idx |= ((unsigned long long)sk[i]) << 8*(idx_len - 1 - i);
hash_key[m-idx_len+i] = sk[i];
}
memcpy(sk_seed, sk+idx_len, n);
@ -626,8 +588,12 @@ int xmssmt_sign(unsigned char *sk, unsigned char *sig_msg, unsigned long long *s
// Message Hash:
// First compute pseudorandom key
prf_m(R, msg, msglen, sk_prf, m);
// Generate hash key (idx || R)
memcpy(hash_key+m, R, m);
// Then use it for message digest
hash_m(msg_h, msg, msglen, R, m, m);
hash_m(msg_h, msg, msglen, hash_key, 2*m, m);
// Start collecting signature
*sig_msg_len = 0;
@ -726,6 +692,7 @@ int xmssmt_sign_open(unsigned char *msg, unsigned long long *msglen, const unsig
unsigned char pkhash[n];
unsigned char root[n];
unsigned char msg_h[m];
unsigned char hash_key[2*m];
unsigned char pub_seed[n];
memcpy(pub_seed, pk+n, n);
@ -736,20 +703,29 @@ int xmssmt_sign_open(unsigned char *msg, unsigned long long *msglen, const unsig
unsigned char node_addr[16];
// Extract index
for(i = 0; i < m-idx_len; i++){
hash_key[i] = 0;
}
for (i = 0; i < idx_len; i++) {
idx |= ((unsigned long long)sig_msg[i]) << (8*(idx_len - 1 - i));
hash_key[m-idx_len+i] = sig_msg[i];
}
printf("verify:: idx = %llu\n", idx);
sig_msg += idx_len;
sig_msg_len -= idx_len;
// hash message (recall, R is now on pole position at sig_msg
unsigned long long tmp_sig_len = m+ (params->d * params->xmss_par.wots_par.keysize) + (params->h * n);
m_len = sig_msg_len - tmp_sig_len;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, sig_msg, m, m);
for(i = 0; i < m; i++){
hash_key[m+i] = sig_msg[i];
}
sig_msg += m;
sig_msg_len -= m;
// hash message (recall, R is now on pole position at sig_msg
unsigned long long tmp_sig_len = (params->d * params->xmss_par.wots_par.keysize) + (params->h * n);
m_len = sig_msg_len - tmp_sig_len;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, hash_key, 2*m, m);
//-----------------------
// Verify signature

3
xmss.h
View File

@ -1,6 +1,7 @@
/*
xmss.h version 20151120
xmss.h version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/

View File

@ -1,6 +1,7 @@
/*
xmss_commons.c version 20151120
xmss_commons.c 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/

View File

@ -1,6 +1,7 @@
/*
xmss_commons.h version 20151120
xmss_commons.h 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/
#ifndef XMSS_COMMONS_H

View File

@ -1,6 +1,7 @@
/*
xmss_fast.c version 20151120
Andreas Hülsing and Joost Rijneveld
xmss_fast.c version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/
@ -15,68 +16,11 @@ Public domain.
#include "hash.h"
#include "prg.h"
#include "xmss_commons.h"
#include "hash_address.h"
// For testing
#include "stdio.h"
/**
* Macros used to manipulate the respective fields
* in the 16byte hash address
*/
#define SET_LAYER_ADDRESS(a, v) {\
a[6] = (a[6] & 3) | ((v << 2) & 252);\
a[5] = (a[5] & 252) | ((v >> 6) & 3);}
#define SET_TREE_ADDRESS(a, v) {\
a[9] = (a[9] & 3) | ((v << 2) & 252);\
a[8] = (v >> 6) & 255;\
a[7] = (v >> 14) & 255;\
a[6] = (a[6] & 252) | ((v >> 22) & 3);}
#define SET_OTS_BIT(a, b) {\
a[9] = (a[9] & 253) | ((b << 1) & 2);}
#define SET_OTS_ADDRESS(a, v) {\
a[12] = (a[12] & 1) | ((v << 1) & 254);\
a[11] = (v >> 7) & 255;\
a[10] = (v >> 15) & 255;\
a[9] = (a[9] & 254) | ((v >> 23) & 1);}
#define ZEROISE_OTS_ADDR(a) {\
a[12] = (a[12] & 254);\
a[13] = 0;\
a[14] = 0;\
a[15] = 0;}
#define SET_LTREE_BIT(a, b) {\
a[9] = (a[9] & 254) | (b & 1);}
#define SET_LTREE_ADDRESS(a, v) {\
a[12] = v & 255;\
a[11] = (v >> 8) & 255;\
a[10] = (v >> 16) & 255;}
#define SET_LTREE_TREE_HEIGHT(a, v) {\
a[13] = (a[13] & 3) | ((v << 2) & 252);}
#define SET_LTREE_TREE_INDEX(a, v) {\
a[15] = (a[15] & 3) | ((v << 2) & 252);\
a[14] = (v >> 6) & 255;\
a[13] = (a[13] & 252) | ((v >> 14) & 3);}
#define SET_NODE_PADDING(a) {\
a[10] = 0;\
a[11] = a[11] & 3;}
#define SET_NODE_TREE_HEIGHT(a, v) {\
a[12] = (a[12] & 3) | ((v << 2) & 252);\
a[11] = (a[11] & 252) | ((v >> 6) & 3);}
#define SET_NODE_TREE_INDEX(a, v) {\
a[15] = (a[15] & 3) | ((v << 2) & 252);\
a[14] = (v >> 6) & 255;\
a[13] = (v >> 14) & 255;\
a[12] = (a[12] & 252) | ((v >> 22) & 3);}
/**
* Used for pseudorandom keygeneration,
@ -614,6 +558,16 @@ int xmss_sign(unsigned char *sk, bds_state *state, unsigned char *sig_msg, unsig
memcpy(sk_prf, sk+4+n, m);
unsigned char pub_seed[n];
memcpy(pub_seed, sk+4+n+m, n);
unsigned char hash_key[2*m];
unsigned long long i;
for(i = 0; i < m-4; i++){
hash_key[i] = 0;
}
for(i = 0; i < 4; i++){
hash_key[i+m-4] = sk[i];
}
// Update SK
sk[0] = ((idx + 1) >> 24) & 255;
@ -624,7 +578,6 @@ int xmss_sign(unsigned char *sk, bds_state *state, unsigned char *sig_msg, unsig
// -- A productive implementation should use a file handle instead and write the updated secret key at this point!
// Init working params
unsigned long long i;
unsigned char R[m];
unsigned char msg_h[m];
unsigned char ots_seed[n];
@ -637,8 +590,10 @@ int xmss_sign(unsigned char *sk, bds_state *state, unsigned char *sig_msg, unsig
// Message Hash:
// First compute pseudorandom key
prf_m(R, msg, msglen, sk_prf, m);
// Generate hash key (idx || R)
memcpy(hash_key+m, R, m);
// Then use it for message digest
hash_m(msg_h, msg, msglen, R, m, m);
hash_m(msg_h, msg, msglen, hash_key, 2*m, m);
// Start collecting signature
*sig_msg_len = 0;
@ -710,6 +665,7 @@ int xmss_sign_open(unsigned char *msg, unsigned long long *msglen, const unsigne
unsigned char pkhash[n];
unsigned char root[n];
unsigned char msg_h[m];
unsigned char hash_key[2*m];
unsigned char pub_seed[n];
memcpy(pub_seed, pk+n, n);
@ -732,16 +688,19 @@ int xmss_sign_open(unsigned char *msg, unsigned long long *msglen, const unsigne
// Extract index
idx = ((unsigned long)sig_msg[0] << 24) | ((unsigned long)sig_msg[1] << 16) | ((unsigned long)sig_msg[2] << 8) | sig_msg[3];
printf("verify:: idx = %lu\n", idx);
sig_msg += 4;
sig_msg_len -= 4;
for(i = 0; i < m-4; i++){
hash_key[i] = 0;
}
for(i = 0; i < m+4; i++){
hash_key[i+m-4] = sig_msg[i];
}
sig_msg += (m+4);
sig_msg_len -= (m+4);
// hash message (recall, R is now on pole position at sig_msg
unsigned long long tmp_sig_len = m+params->wots_par.keysize+params->h*n;
// hash message
unsigned long long tmp_sig_len = params->wots_par.keysize+params->h*n;
m_len = sig_msg_len - tmp_sig_len;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, sig_msg, m, m);
sig_msg += m;
sig_msg_len -= m;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, hash_key, 2*m, m);
//-----------------------
// Verify signature
@ -807,7 +766,7 @@ int xmssmt_keypair(unsigned char *pk, unsigned char *sk, bds_state *states, unsi
// Set address to point on the single tree on layer d-1
unsigned char addr[16] = {0, 0, 0, 0};
SET_OTS_BIT(addr, 1);
SET_TREE_ADDRESS(addr, 0);
SET_TREE_ADDRESS(addr, (unsigned long long)0);
SET_OTS_ADDRESS(addr, 0);
SET_LAYER_ADDRESS(addr, 0);
// Set up state and compute wots signatures for all but topmost tree root
@ -849,15 +808,20 @@ int xmssmt_sign(unsigned char *sk, bds_state *states, unsigned char *wots_sigs,
// Init working params
unsigned char R[m];
unsigned char msg_h[m];
unsigned char hash_key[2*m];
unsigned char ots_seed[n];
unsigned char addr[16] = {0, 0, 0, 0};
unsigned char ots_addr[16] = {0, 0, 0, 0};
bds_state tmp;
// Extract SK
for(i = 0; i < m-idx_len; i++){
hash_key[i] = 0;
}
unsigned long long idx = 0;
for (i = 0; i < idx_len; i++) {
idx |= ((unsigned long long)sk[i]) << 8*(idx_len - 1 - i);
hash_key[m-idx_len+i] = sk[i];
}
memcpy(sk_seed, sk+idx_len, n);
@ -879,8 +843,12 @@ int xmssmt_sign(unsigned char *sk, bds_state *states, unsigned char *wots_sigs,
// Message Hash:
// First compute pseudorandom key
prf_m(R, msg, msglen, sk_prf, m);
// Generate hash key (idx || R)
memcpy(hash_key+m, R, m);
// Then use it for message digest
hash_m(msg_h, msg, msglen, R, m, m);
hash_m(msg_h, msg, msglen, hash_key, 2*m, m);
// Start collecting signature
*sig_msg_len = 0;
@ -1020,6 +988,7 @@ int xmssmt_sign_open(unsigned char *msg, unsigned long long *msglen, const unsig
unsigned char pkhash[n];
unsigned char root[n];
unsigned char msg_h[m];
unsigned char hash_key[2*m];
unsigned char pub_seed[n];
memcpy(pub_seed, pk+n, n);
@ -1030,21 +999,31 @@ int xmssmt_sign_open(unsigned char *msg, unsigned long long *msglen, const unsig
unsigned char node_addr[16];
// Extract index
for(i = 0; i < m-idx_len; i++){
hash_key[i] = 0;
}
for (i = 0; i < idx_len; i++) {
idx |= ((unsigned long long)sig_msg[i]) << (8*(idx_len - 1 - i));
hash_key[m-idx_len+i] = sig_msg[i];
}
printf("verify:: idx = %llu\n", idx);
sig_msg += idx_len;
sig_msg_len -= idx_len;
// hash message (recall, R is now on pole position at sig_msg
unsigned long long tmp_sig_len = m+ (params->d * params->xmss_par.wots_par.keysize) + (params->h * n);
m_len = sig_msg_len - tmp_sig_len;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, sig_msg, m, m);
for(i = 0; i < m; i++){
hash_key[m+i] = sig_msg[i];
}
sig_msg += m;
sig_msg_len -= m;
// hash message (recall, R is now on pole position at sig_msg
unsigned long long tmp_sig_len = (params->d * params->xmss_par.wots_par.keysize) + (params->h * n);
m_len = sig_msg_len - tmp_sig_len;
hash_m(msg_h, sig_msg + tmp_sig_len, m_len, hash_key, 2*m, m);
//-----------------------
// Verify signature
//-----------------------

View File

@ -1,6 +1,7 @@
/*
xmss_fast.h version 20151120
Andreas Hülsing and Joost Rijneveld
xmss_fast.h version 20160210
Andreas Hülsing
Joost Rijneveld
Public domain.
*/