Added crypto.new_hmac() feature. (#1499)
Docs for crypto module refactored for easier maintenance.
This commit is contained in:
parent
19f80abb32
commit
a112296850
|
@ -156,31 +156,22 @@ int ICACHE_FLASH_ATTR crypto_fhash (const digest_mech_info_t *mi,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int ICACHE_FLASH_ATTR crypto_hmac (const digest_mech_info_t *mi,
|
void crypto_hmac_begin (void *ctx, const digest_mech_info_t *mi,
|
||||||
const char *data, size_t data_len,
|
const char *key, size_t key_len, uint8_t *k_opad)
|
||||||
const char *key, size_t key_len,
|
|
||||||
uint8_t *digest)
|
|
||||||
{
|
{
|
||||||
if (!mi)
|
|
||||||
return EINVAL;
|
|
||||||
|
|
||||||
void *ctx = (void *)os_malloc (mi->ctx_size);
|
|
||||||
if (!ctx)
|
|
||||||
return ENOMEM;
|
|
||||||
|
|
||||||
// If key too long, it needs to be hashed before use
|
// If key too long, it needs to be hashed before use
|
||||||
|
char tmp[mi->digest_size];
|
||||||
if (key_len > mi->block_size)
|
if (key_len > mi->block_size)
|
||||||
{
|
{
|
||||||
mi->create (ctx);
|
|
||||||
mi->update (ctx, key, key_len);
|
mi->update (ctx, key, key_len);
|
||||||
mi->finalize (digest, ctx);
|
mi->finalize (tmp, ctx);
|
||||||
key = digest;
|
key = tmp;
|
||||||
key_len = mi->digest_size;
|
key_len = mi->digest_size;
|
||||||
|
mi->create (ctx); // refresh
|
||||||
}
|
}
|
||||||
|
|
||||||
const size_t bs = mi->block_size;
|
const size_t bs = mi->block_size;
|
||||||
uint8_t k_ipad[bs];
|
uint8_t k_ipad[bs];
|
||||||
uint8_t k_opad[bs];
|
|
||||||
|
|
||||||
os_memset (k_ipad, 0x36, bs);
|
os_memset (k_ipad, 0x36, bs);
|
||||||
os_memset (k_opad, 0x5c, bs);
|
os_memset (k_opad, 0x5c, bs);
|
||||||
|
@ -191,16 +182,42 @@ int ICACHE_FLASH_ATTR crypto_hmac (const digest_mech_info_t *mi,
|
||||||
k_opad[i] ^= key[i];
|
k_opad[i] ^= key[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
mi->create (ctx);
|
|
||||||
mi->update (ctx, k_ipad, bs);
|
mi->update (ctx, k_ipad, bs);
|
||||||
mi->update (ctx, data, data_len);
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void crypto_hmac_finalize (void *ctx, const digest_mech_info_t *mi,
|
||||||
|
const uint8_t *k_opad, uint8_t *digest)
|
||||||
|
{
|
||||||
mi->finalize (digest, ctx);
|
mi->finalize (digest, ctx);
|
||||||
|
|
||||||
mi->create (ctx);
|
mi->create (ctx);
|
||||||
mi->update (ctx, k_opad, bs);
|
mi->update (ctx, k_opad, mi->block_size);
|
||||||
mi->update (ctx, digest, mi->digest_size);
|
mi->update (ctx, digest, mi->digest_size);
|
||||||
mi->finalize (digest, ctx);
|
mi->finalize (digest, ctx);
|
||||||
|
}
|
||||||
|
|
||||||
os_free (ctx);
|
|
||||||
|
int crypto_hmac (const digest_mech_info_t *mi,
|
||||||
|
const char *data, size_t data_len,
|
||||||
|
const char *key, size_t key_len,
|
||||||
|
uint8_t *digest)
|
||||||
|
{
|
||||||
|
if (!mi)
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
struct {
|
||||||
|
uint8_t ctx[mi->ctx_size];
|
||||||
|
uint8_t k_opad[mi->block_size];
|
||||||
|
} *tmp = os_malloc (sizeof (*tmp));
|
||||||
|
if (!tmp)
|
||||||
|
return ENOMEM;
|
||||||
|
|
||||||
|
mi->create (tmp->ctx);
|
||||||
|
crypto_hmac_begin (tmp->ctx, mi, key, key_len, tmp->k_opad);
|
||||||
|
mi->update (tmp->ctx, data, data_len);
|
||||||
|
crypto_hmac_finalize (tmp->ctx, mi, tmp->k_opad, digest);
|
||||||
|
|
||||||
|
os_free (tmp);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
@ -66,7 +66,35 @@ int crypto_hash (const digest_mech_info_t *mi, const char *data, size_t data_len
|
||||||
int crypto_fhash (const digest_mech_info_t *mi, read_fn read, int readarg, uint8_t *digest);
|
int crypto_fhash (const digest_mech_info_t *mi, read_fn read, int readarg, uint8_t *digest);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generate a HMAC signature.
|
* Commence calculating a HMAC signature.
|
||||||
|
*
|
||||||
|
* Once this fuction returns successfully, the @c ctx may be updated with
|
||||||
|
* data in multiple passes uses @c mi->update(), before being finalized via
|
||||||
|
* @c crypto_hmac_finalize().
|
||||||
|
*
|
||||||
|
* @param ctx A created context for the given mech @c mi.
|
||||||
|
* @param mi A mech from @c crypto_digest_mech().
|
||||||
|
* @param key The key bytes to use.
|
||||||
|
* @param key_len Number of bytes the @c key comprises.
|
||||||
|
* @param k_opad Buffer of size @c mi->block_size bytes to store the second
|
||||||
|
* round of key material in.
|
||||||
|
* Must be passed to @c crypto_hmac_finalize().
|
||||||
|
*/
|
||||||
|
void crypto_hmac_begin (void *ctx, const digest_mech_info_t *mi, const char *key, size_t key_len, uint8_t *k_opad);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Finalizes calculating a HMAC signature.
|
||||||
|
* @param ctx The created context used with @c crypto_hmac_begin().
|
||||||
|
* @param mi The mech used with @c crypto_hmac_begin().
|
||||||
|
* @param k_opad Second round of keying material, obtained
|
||||||
|
* from @c crypto_hmac_begin().
|
||||||
|
* @param digest Output buffer, must be at least @c mi->digest_size in size.
|
||||||
|
*/
|
||||||
|
void crypto_hmac_finalize (void *ctx, const digest_mech_info_t *mi, const uint8_t *k_opad, uint8_t *digest);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Generate a HMAC signature in one pass.
|
||||||
|
* Implemented in terms of @c crypto_hmac_begin() / @c crypto_hmac_end().
|
||||||
* @param mi A mech from @c crypto_digest_mech(). A null pointer @c mi
|
* @param mi A mech from @c crypto_digest_mech(). A null pointer @c mi
|
||||||
* is harmless, but will of course result in an error return.
|
* is harmless, but will of course result in an error return.
|
||||||
* @param data The data to generate a signature for.
|
* @param data The data to generate a signature for.
|
||||||
|
|
|
@ -9,11 +9,18 @@
|
||||||
#include "vfs.h"
|
#include "vfs.h"
|
||||||
#include "../crypto/digests.h"
|
#include "../crypto/digests.h"
|
||||||
#include "../crypto/mech.h"
|
#include "../crypto/mech.h"
|
||||||
|
#include "lmem.h"
|
||||||
|
|
||||||
#include "user_interface.h"
|
#include "user_interface.h"
|
||||||
|
|
||||||
#include "rom.h"
|
#include "rom.h"
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
const digest_mech_info_t *mech_info;
|
||||||
|
void *ctx;
|
||||||
|
uint8_t *k_opad;
|
||||||
|
} digest_user_datum_t;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* hash = crypto.sha1(input)
|
* hash = crypto.sha1(input)
|
||||||
*
|
*
|
||||||
|
@ -150,11 +157,6 @@ static int crypto_lhash (lua_State *L)
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
typedef struct digest_user_datum_t {
|
|
||||||
const digest_mech_info_t *mech_info;
|
|
||||||
void *ctx;
|
|
||||||
} digest_user_datum_t;
|
|
||||||
|
|
||||||
/* General Usage for extensible hash functions:
|
/* General Usage for extensible hash functions:
|
||||||
* sha = crypto.new_hash("MD5")
|
* sha = crypto.new_hash("MD5")
|
||||||
* sha.update("Data")
|
* sha.update("Data")
|
||||||
|
@ -162,19 +164,30 @@ typedef struct digest_user_datum_t {
|
||||||
* strdigest = crypto.toHex(sha.finalize())
|
* strdigest = crypto.toHex(sha.finalize())
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* crypto.new_hash("MECHTYPE") */
|
#define WANT_HASH 0
|
||||||
static int crypto_new_hash (lua_State *L)
|
#define WANT_HMAC 1
|
||||||
|
|
||||||
|
static int crypto_new_hash_hmac (lua_State *L, int what)
|
||||||
{
|
{
|
||||||
const digest_mech_info_t *mi = crypto_digest_mech (luaL_checkstring (L, 1));
|
const digest_mech_info_t *mi = crypto_digest_mech (luaL_checkstring (L, 1));
|
||||||
if (!mi)
|
if (!mi)
|
||||||
return bad_mech (L);
|
return bad_mech (L);
|
||||||
|
|
||||||
void *ctx = os_malloc (mi->ctx_size);
|
size_t len = 0;
|
||||||
if (ctx==NULL)
|
const char *key = 0;
|
||||||
return bad_mem (L);
|
uint8_t *k_opad = 0;
|
||||||
|
if (what == WANT_HMAC)
|
||||||
|
{
|
||||||
|
key = luaL_checklstring (L, 2, &len);
|
||||||
|
k_opad = luaM_malloc (L, mi->block_size);
|
||||||
|
}
|
||||||
|
void *ctx = luaM_malloc (L, mi->ctx_size);
|
||||||
|
|
||||||
mi->create (ctx);
|
mi->create (ctx);
|
||||||
|
|
||||||
|
if (what == WANT_HMAC)
|
||||||
|
crypto_hmac_begin (ctx, mi, key, len, k_opad);
|
||||||
|
|
||||||
// create a userdataum with specific metatable
|
// create a userdataum with specific metatable
|
||||||
digest_user_datum_t *dudat = (digest_user_datum_t *)lua_newuserdata(L, sizeof(digest_user_datum_t));
|
digest_user_datum_t *dudat = (digest_user_datum_t *)lua_newuserdata(L, sizeof(digest_user_datum_t));
|
||||||
luaL_getmetatable(L, "crypto.hash");
|
luaL_getmetatable(L, "crypto.hash");
|
||||||
|
@ -183,10 +196,24 @@ static int crypto_new_hash (lua_State *L)
|
||||||
// Set pointers to the mechanics and CTX
|
// Set pointers to the mechanics and CTX
|
||||||
dudat->mech_info = mi;
|
dudat->mech_info = mi;
|
||||||
dudat->ctx = ctx;
|
dudat->ctx = ctx;
|
||||||
|
dudat->k_opad = k_opad;
|
||||||
|
|
||||||
return 1; // Pass userdata object back
|
return 1; // Pass userdata object back
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* crypto.new_hash("MECHTYPE") */
|
||||||
|
static int crypto_new_hash (lua_State *L)
|
||||||
|
{
|
||||||
|
return crypto_new_hash_hmac (L, WANT_HASH);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* crypto.new_hmac("MECHTYPE", "KEY") */
|
||||||
|
static int crypto_new_hmac (lua_State *L)
|
||||||
|
{
|
||||||
|
return crypto_new_hash_hmac (L, WANT_HMAC);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/* Called as object, params:
|
/* Called as object, params:
|
||||||
1 - userdata "this"
|
1 - userdata "this"
|
||||||
2 - new string to add to the hash state */
|
2 - new string to add to the hash state */
|
||||||
|
@ -197,7 +224,6 @@ static int crypto_hash_update (lua_State *L)
|
||||||
size_t sl;
|
size_t sl;
|
||||||
|
|
||||||
dudat = (digest_user_datum_t *)luaL_checkudata(L, 1, "crypto.hash");
|
dudat = (digest_user_datum_t *)luaL_checkudata(L, 1, "crypto.hash");
|
||||||
luaL_argcheck(L, dudat, 1, "crypto.hash expected");
|
|
||||||
|
|
||||||
const digest_mech_info_t *mi = dudat->mech_info;
|
const digest_mech_info_t *mi = dudat->mech_info;
|
||||||
|
|
||||||
|
@ -217,12 +243,14 @@ static int crypto_hash_finalize (lua_State *L)
|
||||||
size_t sl;
|
size_t sl;
|
||||||
|
|
||||||
dudat = (digest_user_datum_t *)luaL_checkudata(L, 1, "crypto.hash");
|
dudat = (digest_user_datum_t *)luaL_checkudata(L, 1, "crypto.hash");
|
||||||
luaL_argcheck(L, dudat, 1, "crypto.hash expected");
|
|
||||||
|
|
||||||
const digest_mech_info_t *mi = dudat->mech_info;
|
const digest_mech_info_t *mi = dudat->mech_info;
|
||||||
|
|
||||||
uint8_t digest[mi->digest_size]; // Allocate as local
|
uint8_t digest[mi->digest_size]; // Allocate as local
|
||||||
mi->finalize (digest, dudat->ctx);
|
if (dudat->k_opad)
|
||||||
|
crypto_hmac_finalize (dudat->ctx, mi, dudat->k_opad, digest);
|
||||||
|
else
|
||||||
|
mi->finalize (digest, dudat->ctx);
|
||||||
|
|
||||||
lua_pushlstring (L, digest, sizeof (digest));
|
lua_pushlstring (L, digest, sizeof (digest));
|
||||||
return 1;
|
return 1;
|
||||||
|
@ -235,9 +263,11 @@ static int crypto_hash_gcdelete (lua_State *L)
|
||||||
digest_user_datum_t *dudat;
|
digest_user_datum_t *dudat;
|
||||||
|
|
||||||
dudat = (digest_user_datum_t *)luaL_checkudata(L, 1, "crypto.hash");
|
dudat = (digest_user_datum_t *)luaL_checkudata(L, 1, "crypto.hash");
|
||||||
luaL_argcheck(L, dudat, 1, "crypto.hash expected");
|
|
||||||
|
|
||||||
os_free(dudat->ctx);
|
// luaM_free() uses type info to obtain original size, so have to delve
|
||||||
|
// one level deeper and explicitly pass the size due to void*
|
||||||
|
luaM_realloc_ (L, dudat->ctx, dudat->mech_info->ctx_size, 0);
|
||||||
|
luaM_free (L, dudat->k_opad);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -386,6 +416,7 @@ static const LUA_REG_TYPE crypto_map[] = {
|
||||||
{ LSTRKEY( "fhash" ), LFUNCVAL( crypto_flhash ) },
|
{ LSTRKEY( "fhash" ), LFUNCVAL( crypto_flhash ) },
|
||||||
{ LSTRKEY( "new_hash" ), LFUNCVAL( crypto_new_hash ) },
|
{ LSTRKEY( "new_hash" ), LFUNCVAL( crypto_new_hash ) },
|
||||||
{ LSTRKEY( "hmac" ), LFUNCVAL( crypto_lhmac ) },
|
{ LSTRKEY( "hmac" ), LFUNCVAL( crypto_lhmac ) },
|
||||||
|
{ LSTRKEY( "new_hmac" ), LFUNCVAL( crypto_new_hmac ) },
|
||||||
{ LSTRKEY( "encrypt" ), LFUNCVAL( lcrypto_encrypt ) },
|
{ LSTRKEY( "encrypt" ), LFUNCVAL( lcrypto_encrypt ) },
|
||||||
{ LSTRKEY( "decrypt" ), LFUNCVAL( lcrypto_decrypt ) },
|
{ LSTRKEY( "decrypt" ), LFUNCVAL( lcrypto_decrypt ) },
|
||||||
{ LNILKEY, LNILVAL }
|
{ LNILKEY, LNILVAL }
|
||||||
|
|
|
@ -5,6 +5,16 @@
|
||||||
|
|
||||||
The crypto modules provides various functions for working with cryptographic algorithms.
|
The crypto modules provides various functions for working with cryptographic algorithms.
|
||||||
|
|
||||||
|
The following encryption/decryption algorithms/modes are supported:
|
||||||
|
- `"AES-ECB"` for 128-bit AES in ECB mode (NOT recommended)
|
||||||
|
- `"AES-CBC"` for 128-bit AES in CBC mode
|
||||||
|
|
||||||
|
The following hash algorithms are supported:
|
||||||
|
- MD2 (not available by default, has to be explicitly enabled in `app/include/user_config.h`)
|
||||||
|
- MD5
|
||||||
|
- SHA1
|
||||||
|
- SHA256, SHA384, SHA512 (unless disabled in `app/include/user_config.h`)
|
||||||
|
|
||||||
## crypto.encrypt()
|
## crypto.encrypt()
|
||||||
|
|
||||||
Encrypts Lua strings.
|
Encrypts Lua strings.
|
||||||
|
@ -13,9 +23,7 @@ Encrypts Lua strings.
|
||||||
`crypto.encrypt(algo, key, plain [, iv])`
|
`crypto.encrypt(algo, key, plain [, iv])`
|
||||||
|
|
||||||
#### Parameters
|
#### Parameters
|
||||||
- `algo` the name of the encryption algorithm to use, one of
|
- `algo` the name of a supported encryption algorithm to use
|
||||||
- `"AES-ECB"` for 128-bit AES in ECB mode
|
|
||||||
- `"AES-CBC"` for 128-bit AES in CBC mode
|
|
||||||
- `key` the encryption key as a string; for AES encryption this *MUST* be 16 bytes long
|
- `key` the encryption key as a string; for AES encryption this *MUST* be 16 bytes long
|
||||||
- `plain` the string to encrypt; it will be automatically zero-padded to a 16-byte boundary if necessary
|
- `plain` the string to encrypt; it will be automatically zero-padded to a 16-byte boundary if necessary
|
||||||
- `iv` the initilization vector, if using AES-CBC; defaults to all-zero if not given
|
- `iv` the initilization vector, if using AES-CBC; defaults to all-zero if not given
|
||||||
|
@ -40,9 +48,7 @@ Decrypts previously encrypted data.
|
||||||
`crypto.decrypt(algo, key, cipher [, iv])`
|
`crypto.decrypt(algo, key, cipher [, iv])`
|
||||||
|
|
||||||
#### Parameters
|
#### Parameters
|
||||||
- `algo` the name of the encryption algorithm to use, one of
|
- `algo` the name of a supported encryption algorithm to use
|
||||||
- `"AES-ECB"` for 128-bit AES in ECB mode
|
|
||||||
- `"AES-CBC"` for 128-bit AES in CBC mode
|
|
||||||
- `key` the encryption key as a string; for AES encryption this *MUST* be 16 bytes long
|
- `key` the encryption key as a string; for AES encryption this *MUST* be 16 bytes long
|
||||||
- `cipher` the cipher text to decrypt (as obtained from `crypto.encrypt()`)
|
- `cipher` the cipher text to decrypt (as obtained from `crypto.encrypt()`)
|
||||||
- `iv` the initilization vector, if using AES-CBC; defaults to all-zero if not given
|
- `iv` the initilization vector, if using AES-CBC; defaults to all-zero if not given
|
||||||
|
@ -75,13 +81,6 @@ Compute a cryptographic hash of a a file.
|
||||||
- `algo` the hash algorithm to use, case insensitive string
|
- `algo` the hash algorithm to use, case insensitive string
|
||||||
- `filename` the path to the file to hash
|
- `filename` the path to the file to hash
|
||||||
|
|
||||||
Supported hash algorithms are:
|
|
||||||
|
|
||||||
- MD2 (not available by default, has to be explicitly enabled in `app/include/user_config.h`)
|
|
||||||
- MD5
|
|
||||||
- SHA1
|
|
||||||
- SHA256, SHA384, SHA512 (unless disabled in `app/include/user_config.h`)
|
|
||||||
|
|
||||||
#### Returns
|
#### Returns
|
||||||
A binary string containing the message digest. To obtain the textual version (ASCII hex characters), please use [`crypto.toHex()`](#cryptotohex ).
|
A binary string containing the message digest. To obtain the textual version (ASCII hex characters), please use [`crypto.toHex()`](#cryptotohex ).
|
||||||
|
|
||||||
|
@ -101,13 +100,6 @@ Compute a cryptographic hash of a Lua string.
|
||||||
`algo` the hash algorithm to use, case insensitive string
|
`algo` the hash algorithm to use, case insensitive string
|
||||||
`str` string to hash contents of
|
`str` string to hash contents of
|
||||||
|
|
||||||
Supported hash algorithms are:
|
|
||||||
|
|
||||||
- MD2 (not available by default, has to be explicitly enabled in `app/include/user_config.h`)
|
|
||||||
- MD5
|
|
||||||
- SHA1
|
|
||||||
- SHA256, SHA384, SHA512 (unless disabled in `app/include/user_config.h`)
|
|
||||||
|
|
||||||
#### Returns
|
#### Returns
|
||||||
A binary string containing the message digest. To obtain the textual version (ASCII hex characters), please use [`crypto.toHex()`](#cryptotohex ).
|
A binary string containing the message digest. To obtain the textual version (ASCII hex characters), please use [`crypto.toHex()`](#cryptotohex ).
|
||||||
|
|
||||||
|
@ -126,13 +118,6 @@ Create a digest/hash object that can have any number of strings added to it. Obj
|
||||||
#### Parameters
|
#### Parameters
|
||||||
`algo` the hash algorithm to use, case insensitive string
|
`algo` the hash algorithm to use, case insensitive string
|
||||||
|
|
||||||
Supported hash algorithms are:
|
|
||||||
|
|
||||||
- MD2 (not available by default, has to be explicitly enabled in `app/include/user_config.h`)
|
|
||||||
- MD5
|
|
||||||
- SHA1
|
|
||||||
- SHA256, SHA384, SHA512 (unless disabled in `app/include/user_config.h`)
|
|
||||||
|
|
||||||
#### Returns
|
#### Returns
|
||||||
Userdata object with `update` and `finalize` functions available.
|
Userdata object with `update` and `finalize` functions available.
|
||||||
|
|
||||||
|
@ -157,13 +142,6 @@ Compute a [HMAC](https://en.wikipedia.org/wiki/Hash-based_message_authentication
|
||||||
- `str` data to calculate the hash for
|
- `str` data to calculate the hash for
|
||||||
- `key` key to use for signing, may be a binary string
|
- `key` key to use for signing, may be a binary string
|
||||||
|
|
||||||
Supported hash algorithms are:
|
|
||||||
|
|
||||||
- MD2 (not available by default, has to be explicitly enabled in `app/include/user_config.h`)
|
|
||||||
- MD5
|
|
||||||
- SHA1
|
|
||||||
- SHA256, SHA384, SHA512 (unless disabled in `app/include/user_config.h`)
|
|
||||||
|
|
||||||
#### Returns
|
#### Returns
|
||||||
A binary string containing the HMAC signature. Use [`crypto.toHex()`](#cryptotohex ) to obtain the textual version.
|
A binary string containing the HMAC signature. Use [`crypto.toHex()`](#cryptotohex ) to obtain the textual version.
|
||||||
|
|
||||||
|
@ -172,6 +150,30 @@ A binary string containing the HMAC signature. Use [`crypto.toHex()`](#cryptotoh
|
||||||
print(crypto.toHex(crypto.hmac("sha1","abc","mysecret")))
|
print(crypto.toHex(crypto.hmac("sha1","abc","mysecret")))
|
||||||
```
|
```
|
||||||
|
|
||||||
|
## crypto.new_hmac()
|
||||||
|
|
||||||
|
Create a hmac object that can have any number of strings added to it. Object has `update` and `finalize` functions.
|
||||||
|
|
||||||
|
#### Syntax
|
||||||
|
`hmacobj = crypto.new_hmac(algo, key)`
|
||||||
|
|
||||||
|
#### Parameters
|
||||||
|
- `algo` the hash algorithm to use, case insensitive string
|
||||||
|
- `key` the key to use (may be a binary string)
|
||||||
|
|
||||||
|
#### Returns
|
||||||
|
Userdata object with `update` and `finalize` functions available.
|
||||||
|
|
||||||
|
#### Example
|
||||||
|
```lua
|
||||||
|
hmacobj = crypto.new_hmac("SHA1", "s3kr3t")
|
||||||
|
hmacobj:update("FirstString"))
|
||||||
|
hmacobj:update("SecondString"))
|
||||||
|
digest = hmacobj:finalize()
|
||||||
|
print(crypto.toHex(digest))
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
## crypto.mask()
|
## crypto.mask()
|
||||||
|
|
||||||
Applies an XOR mask to a Lua string. Note that this is not a proper cryptographic mechanism, but some protocols may use it nevertheless.
|
Applies an XOR mask to a Lua string. Note that this is not a proper cryptographic mechanism, but some protocols may use it nevertheless.
|
||||||
|
|
Loading…
Reference in New Issue