[airplay] Update pairing, change ciphering function return values

This commit is contained in:
ejurgensen 2021-01-14 21:29:22 +01:00
parent ccfca52e8d
commit 73c5dcec5a
4 changed files with 20 additions and 22 deletions

View File

@ -102,8 +102,8 @@ struct pair_definition
struct pair_cipher_context *(*pair_cipher_new)(struct pair_definition *type, int channel, const uint8_t *shared_secret, size_t shared_secret_len);
void (*pair_cipher_free)(struct pair_cipher_context *cctx);
int (*pair_encrypt)(uint8_t **ciphertext, size_t *ciphertext_len, uint8_t *plaintext, size_t plaintext_len, struct pair_cipher_context *cctx);
int (*pair_decrypt)(uint8_t **plaintext, size_t *plaintext_len, uint8_t *ciphertext, size_t ciphertext_len, struct pair_cipher_context *cctx);
ssize_t (*pair_encrypt)(uint8_t **ciphertext, size_t *ciphertext_len, uint8_t *plaintext, size_t plaintext_len, struct pair_cipher_context *cctx);
ssize_t (*pair_decrypt)(uint8_t **plaintext, size_t *plaintext_len, uint8_t *ciphertext, size_t ciphertext_len, struct pair_cipher_context *cctx);
};

View File

@ -547,7 +547,7 @@ pair_cipher_errmsg(struct pair_cipher_context *cctx)
return cctx->errmsg;
}
int
ssize_t
pair_encrypt(uint8_t **ciphertext, size_t *ciphertext_len, uint8_t *plaintext, size_t plaintext_len, struct pair_cipher_context *cctx)
{
if (!cctx->type->pair_encrypt)
@ -556,7 +556,7 @@ pair_encrypt(uint8_t **ciphertext, size_t *ciphertext_len, uint8_t *plaintext, s
return cctx->type->pair_encrypt(ciphertext, ciphertext_len, plaintext, plaintext_len, cctx);
}
int
ssize_t
pair_decrypt(uint8_t **plaintext, size_t *plaintext_len, uint8_t *ciphertext, size_t ciphertext_len, struct pair_cipher_context *cctx)
{
if (!cctx->type->pair_decrypt)

View File

@ -102,12 +102,18 @@ pair_cipher_free(struct pair_cipher_context *cctx);
const char *
pair_cipher_errmsg(struct pair_cipher_context *cctx);
/* Return 0 is success, -1 is general error, -2 is ciphertext_len shorter than
* blocklen in payload
/* The return value equals length of plaintext that was encrypted, so if the
* return value == plaintext_len then everything was encrypted. On error -1 is
* returned.
*/
int
ssize_t
pair_encrypt(uint8_t **ciphertext, size_t *ciphertext_len, uint8_t *plaintext, size_t plaintext_len, struct pair_cipher_context *cctx);
int
/* The return value equals length of ciphertext that was decrypted, so if the
* return value == ciphertext_len then everything was decrypted. On error -1 is
* returned.
*/
ssize_t
pair_decrypt(uint8_t **plaintext, size_t *plaintext_len, uint8_t *ciphertext, size_t ciphertext_len, struct pair_cipher_context *cctx);
/* Rolls back the nonce

View File

@ -1729,7 +1729,7 @@ pair_cipher_new(struct pair_definition *type, int channel, const uint8_t *shared
return NULL;
}
static int
static ssize_t
pair_encrypt(uint8_t **ciphertext, size_t *ciphertext_len, uint8_t *plaintext, size_t plaintext_len, struct pair_cipher_context *cctx)
{
uint8_t nonce[NONCE_LENGTH] = { 0 };
@ -1778,17 +1778,14 @@ pair_encrypt(uint8_t **ciphertext, size_t *ciphertext_len, uint8_t *plaintext, s
cctx->encryption_counter++;
}
assert(plain_block == plaintext + plaintext_len);
assert(cipher_block == *ciphertext + *ciphertext_len);
#ifdef DEBUG_PAIR
hexdump("Encrypted:\n", *ciphertext, *ciphertext_len);
#endif
return 0;
return plain_block - plaintext;
}
static int
static ssize_t
pair_decrypt(uint8_t **plaintext, size_t *plaintext_len, uint8_t *ciphertext, size_t ciphertext_len, struct pair_cipher_context *cctx)
{
uint8_t nonce[NONCE_LENGTH] = { 0 };
@ -1812,10 +1809,8 @@ pair_decrypt(uint8_t **plaintext, size_t *plaintext_len, uint8_t *ciphertext, si
memcpy(&block_len, cipher_block, sizeof(block_len)); // TODO BE or LE?
if (cipher_block + block_len + sizeof(block_len) + AUTHTAG_LENGTH > ciphertext + ciphertext_len)
{
cctx->errmsg = "Insufficient encrypted data or corrupt block length";
cctx->decryption_counter = cctx->decryption_counter_prev;
free(*plaintext);
return -2; // Corrupt block_len, stop before we read over the end
// The remaining ciphertext doesn't contain an entire block, so stop
break;
}
memcpy(tag, cipher_block + sizeof(block_len) + block_len, sizeof(tag));
@ -1835,16 +1830,13 @@ pair_decrypt(uint8_t **plaintext, size_t *plaintext_len, uint8_t *ciphertext, si
cctx->decryption_counter++;
}
assert(plain_block < *plaintext + ciphertext_len);
assert(cipher_block == ciphertext + ciphertext_len);
*plaintext_len = plain_block - *plaintext;
#ifdef DEBUG_PAIR
hexdump("Decrypted:\n", *plaintext, *plaintext_len);
#endif
return 0;
return cipher_block - ciphertext;
}
const struct pair_definition pair_homekit_normal =