static gboolean
purple_aes_cipher_gnutls_decrypt(const guchar *input, guchar *output, size_t len,
	guchar iv[PURPLE_AES_BLOCK_SIZE], guchar key[32], guint key_size,
	PurpleCipherBatchMode batch_mode)
{
	gnutls_cipher_hd_t handle;
	int ret;

	/* We have to simulate ECB mode, which is not supported by GnuTLS. */
	if (batch_mode == PURPLE_CIPHER_BATCH_MODE_ECB) {
		size_t i;
		for (i = 0; i < len / PURPLE_AES_BLOCK_SIZE; i++) {
			int offset = i * PURPLE_AES_BLOCK_SIZE;
			guchar iv_local[PURPLE_AES_BLOCK_SIZE];
			gboolean succ;

			memcpy(iv_local, iv, sizeof(iv_local));
			succ = purple_aes_cipher_gnutls_decrypt(
				input + offset, output + offset,
				PURPLE_AES_BLOCK_SIZE,
				iv_local, key, key_size,
				PURPLE_CIPHER_BATCH_MODE_CBC);
			if (!succ)
				return FALSE;
		}
		return TRUE;
	}

	handle = purple_aes_cipher_gnutls_crypt_init(iv, key, key_size);
	if (handle == NULL)
		return FALSE;

	ret = gnutls_cipher_decrypt2(handle, input, len, output, len);
	gnutls_cipher_deinit(handle);

	if (ret != 0) {
		purple_debug_error("cipher-aes",
			"gnutls_cipher_decrypt2 failed: %d\n", ret);
		return FALSE;
	}

	return TRUE;
}
Exemple #2
0
static gboolean
purple_aes_cipher_gnutls_decrypt(const guchar *input, guchar *output, size_t len,
	guchar iv[PURPLE_AES_BLOCK_SIZE], guchar key[32], guint key_size)
{
	gnutls_cipher_hd_t handle;
	int ret;

	handle = purple_aes_cipher_gnutls_crypt_init(iv, key, key_size);
	if (handle == NULL)
		return FALSE;

	ret = gnutls_cipher_decrypt2(handle, input, len, output, len);
	gnutls_cipher_deinit(handle);

	if (ret != 0) {
		purple_debug_error("cipher-aes",
			"gnutls_cipher_decrypt2 failed: %d\n", ret);
		return FALSE;
	}

	return TRUE;
}