mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager.git
synced 2026-01-10 21:00:23 +01:00
libnm-core: reimplement crypto_md5_hash() using GChecksum
Reimplement crypto_md5_hash() using GChecksum. Remove the gboolean return value and GError argument, since it cannot fail now.
This commit is contained in:
parent
34519eee13
commit
48ff21b5bc
6 changed files with 66 additions and 171 deletions
|
|
@ -404,25 +404,15 @@ make_des_aes_key (const char *cipher,
|
|||
|
||||
key = g_malloc0 (digest_len + 1);
|
||||
|
||||
if (!crypto_md5_hash (salt,
|
||||
salt_len,
|
||||
password,
|
||||
strlen (password),
|
||||
key,
|
||||
digest_len,
|
||||
error))
|
||||
goto error;
|
||||
crypto_md5_hash (salt,
|
||||
salt_len,
|
||||
password,
|
||||
strlen (password),
|
||||
key,
|
||||
digest_len);
|
||||
|
||||
*out_len = digest_len;
|
||||
return key;
|
||||
|
||||
error:
|
||||
if (key) {
|
||||
/* Don't leak stale key material */
|
||||
memset (key, 0, digest_len);
|
||||
g_free (key);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static GByteArray *
|
||||
|
|
@ -746,3 +736,51 @@ crypto_verify_private_key (const char *filename,
|
|||
}
|
||||
return format;
|
||||
}
|
||||
|
||||
void
|
||||
crypto_md5_hash (const char *salt,
|
||||
const gsize salt_len,
|
||||
const char *password,
|
||||
gsize password_len,
|
||||
char *buffer,
|
||||
gsize buflen)
|
||||
{
|
||||
GChecksum *ctx;
|
||||
int nkey = buflen;
|
||||
gsize digest_len;
|
||||
int count = 0;
|
||||
char digest[16];
|
||||
char *p = buffer;
|
||||
|
||||
g_assert_cmpint (g_checksum_type_get_length (G_CHECKSUM_MD5), ==, sizeof (digest));
|
||||
|
||||
if (salt)
|
||||
g_return_if_fail (salt_len >= 8);
|
||||
|
||||
g_return_if_fail (password != NULL);
|
||||
g_return_if_fail (password_len > 0);
|
||||
g_return_if_fail (buffer != NULL);
|
||||
g_return_if_fail (buflen > 0);
|
||||
|
||||
ctx = g_checksum_new (G_CHECKSUM_MD5);
|
||||
|
||||
while (nkey > 0) {
|
||||
int i = 0;
|
||||
|
||||
g_checksum_reset (ctx);
|
||||
if (count++)
|
||||
g_checksum_update (ctx, (const guchar *) digest, digest_len);
|
||||
g_checksum_update (ctx, (const guchar *) password, password_len);
|
||||
if (salt)
|
||||
g_checksum_update (ctx, (const guchar *) salt, 8); /* Only use 8 bytes of salt */
|
||||
g_checksum_get_digest (ctx, (guchar *) digest, &digest_len);
|
||||
|
||||
while (nkey && (i < digest_len)) {
|
||||
*(p++) = digest[i++];
|
||||
nkey--;
|
||||
}
|
||||
}
|
||||
|
||||
memset (digest, 0, sizeof (digest));
|
||||
g_checksum_free (ctx);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -78,13 +78,12 @@ NMCryptoFileFormat crypto_verify_private_key (const char *file,
|
|||
|
||||
/* Internal utils API bits for crypto providers */
|
||||
|
||||
gboolean crypto_md5_hash (const char *salt,
|
||||
const gsize salt_len,
|
||||
const char *password,
|
||||
gsize password_len,
|
||||
char *buffer,
|
||||
gsize buflen,
|
||||
GError **error);
|
||||
void crypto_md5_hash (const char *salt,
|
||||
const gsize salt_len,
|
||||
const char *password,
|
||||
gsize password_len,
|
||||
char *buffer,
|
||||
gsize buflen);
|
||||
|
||||
char * crypto_decrypt (const char *cipher,
|
||||
int key_type,
|
||||
|
|
|
|||
|
|
@ -56,63 +56,6 @@ crypto_init (GError **error)
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
crypto_md5_hash (const char *salt,
|
||||
const gsize salt_len,
|
||||
const char *password,
|
||||
gsize password_len,
|
||||
char *buffer,
|
||||
gsize buflen,
|
||||
GError **error)
|
||||
{
|
||||
gcry_md_hd_t ctx;
|
||||
gcry_error_t err;
|
||||
int nkey = buflen;
|
||||
const gsize digest_len = 16;
|
||||
int count = 0;
|
||||
char digest[MD5_HASH_LEN];
|
||||
char *p = buffer;
|
||||
|
||||
if (salt)
|
||||
g_return_val_if_fail (salt_len >= SALT_LEN, FALSE);
|
||||
|
||||
g_return_val_if_fail (password != NULL, FALSE);
|
||||
g_return_val_if_fail (password_len > 0, FALSE);
|
||||
g_return_val_if_fail (buffer != NULL, FALSE);
|
||||
g_return_val_if_fail (buflen > 0, FALSE);
|
||||
|
||||
err = gcry_md_open (&ctx, GCRY_MD_MD5, 0);
|
||||
if (err) {
|
||||
g_set_error (error, NM_CRYPTO_ERROR,
|
||||
NM_CRYPTO_ERROR_FAILED,
|
||||
_("Failed to initialize the MD5 engine: %s / %s."),
|
||||
gcry_strsource (err), gcry_strerror (err));
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
while (nkey > 0) {
|
||||
int i = 0;
|
||||
|
||||
if (count++)
|
||||
gcry_md_write (ctx, digest, digest_len);
|
||||
gcry_md_write (ctx, password, password_len);
|
||||
if (salt)
|
||||
gcry_md_write (ctx, salt, SALT_LEN); /* Only use 8 bytes of salt */
|
||||
gcry_md_final (ctx);
|
||||
memcpy (digest, gcry_md_read (ctx, 0), digest_len);
|
||||
gcry_md_reset (ctx);
|
||||
|
||||
while (nkey && (i < digest_len)) {
|
||||
*(p++) = digest[i++];
|
||||
nkey--;
|
||||
}
|
||||
}
|
||||
|
||||
memset (digest, 0, sizeof (digest));
|
||||
gcry_md_close (ctx);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
char *
|
||||
crypto_decrypt (const char *cipher,
|
||||
int key_type,
|
||||
|
|
|
|||
|
|
@ -72,61 +72,6 @@ crypto_init (GError **error)
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
crypto_md5_hash (const char *salt,
|
||||
const gsize salt_len,
|
||||
const char *password,
|
||||
gsize password_len,
|
||||
char *buffer,
|
||||
gsize buflen,
|
||||
GError **error)
|
||||
{
|
||||
PK11Context *ctx;
|
||||
int nkey = buflen;
|
||||
unsigned int digest_len;
|
||||
int count = 0;
|
||||
char digest[MD5_HASH_LEN];
|
||||
char *p = buffer;
|
||||
|
||||
if (salt)
|
||||
g_return_val_if_fail (salt_len >= 8, FALSE);
|
||||
|
||||
g_return_val_if_fail (password != NULL, FALSE);
|
||||
g_return_val_if_fail (password_len > 0, FALSE);
|
||||
g_return_val_if_fail (buffer != NULL, FALSE);
|
||||
g_return_val_if_fail (buflen > 0, FALSE);
|
||||
|
||||
ctx = PK11_CreateDigestContext (SEC_OID_MD5);
|
||||
if (!ctx) {
|
||||
g_set_error (error, NM_CRYPTO_ERROR,
|
||||
NM_CRYPTO_ERROR_FAILED,
|
||||
_("Failed to initialize the MD5 context: %d."),
|
||||
PORT_GetError ());
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
while (nkey > 0) {
|
||||
int i = 0;
|
||||
|
||||
PK11_DigestBegin (ctx);
|
||||
if (count++)
|
||||
PK11_DigestOp (ctx, (const unsigned char *) digest, digest_len);
|
||||
PK11_DigestOp (ctx, (const unsigned char *) password, password_len);
|
||||
if (salt)
|
||||
PK11_DigestOp (ctx, (const unsigned char *) salt, 8); /* Only use 8 bytes of salt */
|
||||
PK11_DigestFinal (ctx, (unsigned char *) digest, &digest_len, sizeof (digest));
|
||||
|
||||
while (nkey && (i < digest_len)) {
|
||||
*(p++) = digest[i++];
|
||||
nkey--;
|
||||
}
|
||||
}
|
||||
|
||||
memset (digest, 0, sizeof (digest));
|
||||
PK11_DestroyContext (ctx, PR_TRUE);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
char *
|
||||
crypto_decrypt (const char *cipher,
|
||||
int key_type,
|
||||
|
|
|
|||
|
|
@ -1976,33 +1976,15 @@ nm_utils_uuid_generate (void)
|
|||
char *
|
||||
nm_utils_uuid_generate_from_string (const char *s)
|
||||
{
|
||||
GError *error = NULL;
|
||||
uuid_t *uuid;
|
||||
char *buf = NULL;
|
||||
|
||||
if (!nm_utils_init (&error)) {
|
||||
g_warning ("error initializing crypto: (%d) %s",
|
||||
error ? error->code : 0,
|
||||
error ? error->message : "unknown");
|
||||
if (error)
|
||||
g_error_free (error);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
uuid = g_malloc0 (sizeof (*uuid));
|
||||
if (!crypto_md5_hash (NULL, 0, s, strlen (s), (char *) uuid, sizeof (*uuid), &error)) {
|
||||
g_warning ("error generating UUID: (%d) %s",
|
||||
error ? error->code : 0,
|
||||
error ? error->message : "unknown");
|
||||
if (error)
|
||||
g_error_free (error);
|
||||
goto out;
|
||||
}
|
||||
crypto_md5_hash (NULL, 0, s, strlen (s), (char *) uuid, sizeof (*uuid));
|
||||
|
||||
buf = g_malloc0 (37);
|
||||
uuid_unparse_lower (*uuid, &buf[0]);
|
||||
|
||||
out:
|
||||
g_free (uuid);
|
||||
return buf;
|
||||
}
|
||||
|
|
@ -2012,8 +1994,7 @@ make_key (const char *cipher,
|
|||
const char *salt,
|
||||
const gsize salt_len,
|
||||
const char *password,
|
||||
gsize *out_len,
|
||||
GError **error)
|
||||
gsize *out_len)
|
||||
{
|
||||
char *key;
|
||||
guint32 digest_len = 24; /* DES-EDE3-CBC */
|
||||
|
|
@ -2030,13 +2011,8 @@ make_key (const char *cipher,
|
|||
|
||||
key = g_malloc0 (digest_len + 1);
|
||||
|
||||
if (!crypto_md5_hash (salt, salt_len, password, strlen (password), key, digest_len, error)) {
|
||||
*out_len = 0;
|
||||
memset (key, 0, digest_len);
|
||||
g_free (key);
|
||||
key = NULL;
|
||||
} else
|
||||
*out_len = digest_len;
|
||||
crypto_md5_hash (salt, salt_len, password, strlen (password), key, digest_len);
|
||||
*out_len = digest_len;
|
||||
|
||||
return key;
|
||||
}
|
||||
|
|
@ -2097,10 +2073,7 @@ nm_utils_rsa_key_encrypt_helper (const char *cipher,
|
|||
if (!crypto_randomize (salt, salt_len, error))
|
||||
goto out;
|
||||
|
||||
key = make_key (cipher, &salt[0], salt_len, in_password, &key_len, error);
|
||||
if (!key)
|
||||
goto out;
|
||||
|
||||
key = make_key (cipher, &salt[0], salt_len, in_password, &key_len);
|
||||
enc = crypto_encrypt (cipher, data, len, salt, salt_len, key, key_len, &enc_len, error);
|
||||
if (!enc)
|
||||
goto out;
|
||||
|
|
|
|||
|
|
@ -435,7 +435,6 @@ test_md5 (void)
|
|||
{
|
||||
char digest[LONG_DIGEST], *hex;
|
||||
int i;
|
||||
GError *error = NULL;
|
||||
|
||||
for (i = 0; i < G_N_ELEMENTS (md5_tests); i++) {
|
||||
memset (digest, 0, sizeof (digest));
|
||||
|
|
@ -443,9 +442,7 @@ test_md5 (void)
|
|||
md5_tests[i].salt ? strlen (md5_tests[i].salt) : 0,
|
||||
md5_tests[i].password,
|
||||
strlen (md5_tests[i].password),
|
||||
digest, md5_tests[i].digest_size,
|
||||
&error);
|
||||
g_assert_no_error (error);
|
||||
digest, md5_tests[i].digest_size);
|
||||
|
||||
hex = nm_utils_bin2hexstr (digest, md5_tests[i].digest_size, -1);
|
||||
g_assert_cmpstr (hex, ==, md5_tests[i].result);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue