futility: Use only vboot 2.0 APIs for keyblocks
[vboot.git] / host / lib / host_signature2.c
1 /* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
2  * Use of this source code is governed by a BSD-style license that can be
3  * found in the LICENSE file.
4  *
5  * Host functions for signature generation.
6  */
7
8 #include <openssl/rsa.h>
9
10 #include <stdio.h>
11 #include <stdlib.h>
12 #include <sys/types.h>
13 #include <sys/wait.h>
14 #include <unistd.h>
15
16 #include "2sysincludes.h"
17
18 #include "2common.h"
19 #include "2rsa.h"
20 #include "2sha.h"
21 #include "cryptolib.h"
22 #include "file_keys.h"
23 #include "host_common.h"
24 #include "host_key2.h"
25 #include "host_signature2.h"
26 #include "vb2_common.h"
27 #include "vboot_common.h"
28
29 struct vb2_signature *vb2_alloc_signature(uint32_t sig_size,
30                                           uint32_t data_size)
31 {
32         struct vb2_signature *sig = (struct vb2_signature *)
33                 calloc(sizeof(*sig) + sig_size, 1);
34         if (!sig)
35                 return NULL;
36
37         sig->sig_offset = sizeof(*sig);
38         sig->sig_size = sig_size;
39         sig->data_size = data_size;
40
41         return sig;
42 }
43
44 void vb2_init_signature(struct vb2_signature *sig, uint8_t *sig_data,
45                         uint32_t sig_size, uint32_t data_size)
46 {
47         memset(sig, 0, sizeof(*sig));
48         sig->sig_offset = vb2_offset_of(sig, sig_data);
49         sig->sig_size = sig_size;
50         sig->data_size = data_size;
51 }
52
53 int vb2_copy_signature(struct vb2_signature *dest,
54                        const struct vb2_signature *src)
55 {
56         if (dest->sig_size < src->sig_size)
57                 return VB2_ERROR_SIG_SIZE;
58
59         dest->sig_size = src->sig_size;
60         dest->data_size = src->data_size;
61
62         memcpy(vb2_signature_data(dest),
63                vb2_signature_data((struct vb2_signature *)src),
64                src->sig_size);
65
66         return VB2_SUCCESS;
67 }
68
69 struct vb2_signature *vb2_sha512_signature(const uint8_t *data, uint32_t size)
70 {
71         uint8_t digest[VB2_SHA512_DIGEST_SIZE];
72         if (VB2_SUCCESS != vb2_digest_buffer(data, size, VB2_HASH_SHA512,
73                                              digest, sizeof(digest)))
74                 return NULL;
75
76         struct vb2_signature *sig =
77                 vb2_alloc_signature(VB2_SHA512_DIGEST_SIZE, size);
78         if (!sig)
79                 return NULL;
80
81         memcpy(vb2_signature_data(sig), digest, VB2_SHA512_DIGEST_SIZE);
82         return sig;
83 }
84
85 struct vb2_signature *vb2_calculate_signature(
86                 const uint8_t *data, uint32_t size,
87                 const struct vb2_private_key *key)
88 {
89         uint8_t digest[VB2_MAX_DIGEST_SIZE];
90         uint32_t digest_size = vb2_digest_size(key->hash_alg);
91
92         uint32_t digest_info_size = 0;
93         const uint8_t *digest_info = NULL;
94         if (VB2_SUCCESS != vb2_digest_info(key->hash_alg,
95                                            &digest_info, &digest_info_size))
96                 return NULL;
97
98         /* Calculate the digest */
99         if (VB2_SUCCESS != vb2_digest_buffer(data, size, key->hash_alg,
100                                              digest, digest_size))
101                 return NULL;
102
103         /* Prepend the digest info to the digest */
104         int signature_digest_len = digest_size + digest_info_size;
105         uint8_t *signature_digest = malloc(signature_digest_len);
106         if (!signature_digest)
107                 return NULL;
108
109         memcpy(signature_digest, digest_info, digest_info_size);
110         memcpy(signature_digest + digest_info_size, digest, digest_size);
111
112         /* Allocate output signature */
113         struct vb2_signature *sig = (struct vb2_signature *)
114                 vb2_alloc_signature(vb2_rsa_sig_size(key->sig_alg), size);
115         if (!sig) {
116                 free(signature_digest);
117                 return NULL;
118         }
119
120         /* Sign the signature_digest into our output buffer */
121         int rv = RSA_private_encrypt(signature_digest_len,    /* Input length */
122                                      signature_digest,        /* Input data */
123                                      vb2_signature_data(sig), /* Output sig */
124                                      key->rsa_private_key,    /* Key to use */
125                                      RSA_PKCS1_PADDING);      /* Padding */
126         free(signature_digest);
127
128         if (-1 == rv) {
129                 VB2_DEBUG("%s: RSA_private_encrypt() failed.\n", __func__);
130                 free(sig);
131                 return NULL;
132         }
133
134         /* Return the signature */
135         return sig;
136 }