in source/windows/bcrypt_ecc.c [85:139]
static int s_sign_message(
const struct aws_ecc_key_pair *key_pair,
const struct aws_byte_cursor *message,
struct aws_byte_buf *signature_output) {
struct bcrypt_ecc_key_pair *key_impl = key_pair->impl;
size_t output_buf_space = signature_output->capacity - signature_output->len;
if (output_buf_space < s_signature_length(key_pair)) {
return aws_raise_error(AWS_ERROR_SHORT_BUFFER);
}
uint8_t temp_signature[MAX_SIGNATURE_LENGTH] = {0};
struct aws_byte_buf temp_signature_buf = aws_byte_buf_from_empty_array(temp_signature, sizeof(temp_signature));
size_t signature_length = temp_signature_buf.capacity;
NTSTATUS status = BCryptSignHash(
key_impl->key_handle,
NULL,
message->ptr,
(ULONG)message->len,
temp_signature_buf.buffer,
(ULONG)signature_length,
(ULONG *)&signature_length,
0);
if (status != 0) {
return aws_raise_error(AWS_ERROR_INVALID_ARGUMENT);
}
temp_signature_buf.len += signature_length;
size_t coordinate_len = temp_signature_buf.len / 2;
/* okay. Windows doesn't DER encode this to ASN.1, so we need to do it manually. */
struct aws_der_encoder *encoder =
aws_der_encoder_new(key_pair->allocator, signature_output->capacity - signature_output->len);
if (!encoder) {
return AWS_OP_ERR;
}
aws_der_encoder_begin_sequence(encoder);
struct aws_byte_cursor integer_cur = aws_byte_cursor_from_array(temp_signature_buf.buffer, coordinate_len);
aws_der_encoder_write_integer(encoder, integer_cur);
integer_cur = aws_byte_cursor_from_array(temp_signature_buf.buffer + coordinate_len, coordinate_len);
aws_der_encoder_write_integer(encoder, integer_cur);
aws_der_encoder_end_sequence(encoder);
struct aws_byte_cursor signature_out_cur;
AWS_ZERO_STRUCT(signature_out_cur);
aws_der_encoder_get_contents(encoder, &signature_out_cur);
aws_byte_buf_append(signature_output, &signature_out_cur);
aws_der_encoder_destroy(encoder);
return AWS_OP_SUCCESS;
}