| OLD | NEW |
| 1 /* Copyright (c) 2010 The Chromium OS Authors. All rights reserved. | 1 /* Copyright (c) 2010 The Chromium OS Authors. All rights reserved. |
| 2 * Use of this source code is governed by a BSD-style license that can be | 2 * Use of this source code is governed by a BSD-style license that can be |
| 3 * found in the LICENSE file. | 3 * found in the LICENSE file. |
| 4 * | 4 * |
| 5 * High-level firmware API for loading and verifying rewritable firmware. | 5 * High-level firmware API for loading and verifying rewritable firmware. |
| 6 * (Firmware portion) | 6 * (Firmware portion) |
| 7 */ | 7 */ |
| 8 | 8 |
| 9 #include "load_firmware_fw.h" | 9 #include "load_firmware_fw.h" |
| 10 #include "rollback_index.h" | 10 #include "rollback_index.h" |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 44 int index; | 44 int index; |
| 45 | 45 |
| 46 /* Clear output params in case we fail */ | 46 /* Clear output params in case we fail */ |
| 47 params->firmware_index = 0; | 47 params->firmware_index = 0; |
| 48 params->kernel_sign_key_blob = NULL; | 48 params->kernel_sign_key_blob = NULL; |
| 49 params->kernel_sign_key_size = 0; | 49 params->kernel_sign_key_size = 0; |
| 50 | 50 |
| 51 debug("LoadFirmware started...\n"); | 51 debug("LoadFirmware started...\n"); |
| 52 | 52 |
| 53 /* Must have a root key */ | 53 /* Must have a root key */ |
| 54 if (!root_key) | 54 if (!root_key) { |
| 55 debug("No root key\n"); |
| 55 return LOAD_FIRMWARE_RECOVERY; | 56 return LOAD_FIRMWARE_RECOVERY; |
| 57 } |
| 56 | 58 |
| 57 /* Initialize the TPM and read rollback indices. */ | 59 /* Initialize the TPM and read rollback indices. */ |
| 58 /* TODO: fix SetupTPM parameter for developer mode */ | 60 /* TODO: fix SetupTPM parameter for developer mode */ |
| 59 if (0 != SetupTPM(RO_NORMAL_MODE, 0) ) | 61 if (0 != SetupTPM(RO_NORMAL_MODE, 0)) { |
| 62 debug("SetupTPM failed\n"); |
| 60 return LOAD_FIRMWARE_RECOVERY; | 63 return LOAD_FIRMWARE_RECOVERY; |
| 64 } |
| 61 if (0 != GetStoredVersions(FIRMWARE_VERSIONS, | 65 if (0 != GetStoredVersions(FIRMWARE_VERSIONS, |
| 62 &tpm_key_version, &tpm_fw_version)) | 66 &tpm_key_version, &tpm_fw_version)) { |
| 67 debug("Unable to get stored versions.\n"); |
| 63 return LOAD_FIRMWARE_RECOVERY; | 68 return LOAD_FIRMWARE_RECOVERY; |
| 69 } |
| 64 | 70 |
| 65 /* Allocate our internal data */ | 71 /* Allocate our internal data */ |
| 66 lfi = (VbLoadFirmwareInternal*)Malloc(sizeof(VbLoadFirmwareInternal)); | 72 lfi = (VbLoadFirmwareInternal*)Malloc(sizeof(VbLoadFirmwareInternal)); |
| 67 if (!lfi) | 73 if (!lfi) |
| 68 return LOAD_FIRMWARE_RECOVERY; | 74 return LOAD_FIRMWARE_RECOVERY; |
| 69 params->load_firmware_internal = (uint8_t*)lfi; | 75 params->load_firmware_internal = (uint8_t*)lfi; |
| 70 | 76 |
| 71 /* Loop over indices */ | 77 /* Loop over indices */ |
| 72 for (index = 0; index < 2; index++) { | 78 for (index = 0; index < 2; index++) { |
| 73 VbKeyBlockHeader* key_block; | 79 VbKeyBlockHeader* key_block; |
| 74 uint64_t vblock_size; | 80 uint64_t vblock_size; |
| 75 VbFirmwarePreambleHeader* preamble; | 81 VbFirmwarePreambleHeader* preamble; |
| 76 RSAPublicKey* data_key; | 82 RSAPublicKey* data_key; |
| 77 uint64_t key_version; | 83 uint64_t key_version; |
| 78 uint8_t* body_digest; | 84 uint8_t* body_digest; |
| 79 | 85 |
| 80 /* Verify the key block */ | 86 /* Verify the key block */ |
| 81 if (0 == index) { | 87 if (0 == index) { |
| 82 key_block = (VbKeyBlockHeader*)params->verification_block_0; | 88 key_block = (VbKeyBlockHeader*)params->verification_block_0; |
| 83 vblock_size = params->verification_size_0; | 89 vblock_size = params->verification_size_0; |
| 84 } else { | 90 } else { |
| 85 key_block = (VbKeyBlockHeader*)params->verification_block_1; | 91 key_block = (VbKeyBlockHeader*)params->verification_block_1; |
| 86 vblock_size = params->verification_size_1; | 92 vblock_size = params->verification_size_1; |
| 87 } | 93 } |
| 88 if ((0 != KeyBlockVerify(key_block, vblock_size, root_key))) | 94 if ((0 != KeyBlockVerify(key_block, vblock_size, root_key))) { |
| 95 debug("Key block verification failed.\n"); |
| 89 continue; | 96 continue; |
| 97 } |
| 90 | 98 |
| 91 /* Check for rollback of key version. */ | 99 /* Check for rollback of key version. */ |
| 92 key_version = key_block->data_key.key_version; | 100 key_version = key_block->data_key.key_version; |
| 93 if (key_version < tpm_key_version) | 101 if (key_version < tpm_key_version) { |
| 102 debug("Key rollback detected.\n"); |
| 94 continue; | 103 continue; |
| 104 } |
| 95 | 105 |
| 96 /* Get the key for preamble/data verification from the key block. */ | 106 /* Get the key for preamble/data verification from the key block. */ |
| 97 data_key = PublicKeyToRSA(&key_block->data_key); | 107 data_key = PublicKeyToRSA(&key_block->data_key); |
| 98 if (!data_key) | 108 if (!data_key) { |
| 109 debug("Unable to parse data key.\n"); |
| 99 continue; | 110 continue; |
| 111 } |
| 100 | 112 |
| 101 /* Verify the preamble, which follows the key block. */ | 113 /* Verify the preamble, which follows the key block. */ |
| 102 preamble = (VbFirmwarePreambleHeader*)((uint8_t*)key_block + | 114 preamble = (VbFirmwarePreambleHeader*)((uint8_t*)key_block + |
| 103 key_block->key_block_size); | 115 key_block->key_block_size); |
| 104 if ((0 != VerifyFirmwarePreamble2(preamble, | 116 if ((0 != VerifyFirmwarePreamble2(preamble, |
| 105 vblock_size - key_block->key_block_size, | 117 vblock_size - key_block->key_block_size, |
| 106 data_key))) { | 118 data_key))) { |
| 119 debug("Preamble verfication failed.\n"); |
| 107 RSAPublicKeyFree(data_key); | 120 RSAPublicKeyFree(data_key); |
| 108 continue; | 121 continue; |
| 109 } | 122 } |
| 110 | 123 |
| 111 /* Check for rollback of firmware version. */ | 124 /* Check for rollback of firmware version. */ |
| 112 if (key_version == tpm_key_version && | 125 if (key_version == tpm_key_version && |
| 113 preamble->firmware_version < tpm_fw_version) { | 126 preamble->firmware_version < tpm_fw_version) { |
| 127 debug("Firmware version rollback detected.\n"); |
| 114 RSAPublicKeyFree(data_key); | 128 RSAPublicKeyFree(data_key); |
| 115 continue; | 129 continue; |
| 116 } | 130 } |
| 117 | 131 |
| 118 /* Check for lowest key version from a valid header. */ | 132 /* Check for lowest key version from a valid header. */ |
| 119 if (lowest_key_version > key_version) { | 133 if (lowest_key_version > key_version) { |
| 120 lowest_key_version = key_version; | 134 lowest_key_version = key_version; |
| 121 lowest_fw_version = preamble->firmware_version; | 135 lowest_fw_version = preamble->firmware_version; |
| 122 } | 136 } |
| 123 else if (lowest_key_version == key_version && | 137 else if (lowest_key_version == key_version && |
| 124 lowest_fw_version > preamble->firmware_version) { | 138 lowest_fw_version > preamble->firmware_version) { |
| 125 lowest_fw_version = preamble->firmware_version; | 139 lowest_fw_version = preamble->firmware_version; |
| 126 } | 140 } |
| 127 | 141 |
| 128 /* If we already have good firmware, no need to read another one; | 142 /* If we already have good firmware, no need to read another one; |
| 129 * we only needed to look at the versions to check for | 143 * we only needed to look at the versions to check for |
| 130 * rollback. */ | 144 * rollback. */ |
| 131 if (-1 != good_index) | 145 if (-1 != good_index) |
| 132 continue; | 146 continue; |
| 133 | 147 |
| 134 /* Read the firmware data */ | 148 /* Read the firmware data */ |
| 135 DigestInit(&lfi->body_digest_context, data_key->algorithm); | 149 DigestInit(&lfi->body_digest_context, data_key->algorithm); |
| 136 lfi->body_size_accum = 0; | 150 lfi->body_size_accum = 0; |
| 137 if ((0 != GetFirmwareBody(params, index)) || | 151 if (0 != GetFirmwareBody(params, index)) { |
| 138 (lfi->body_size_accum != preamble->body_signature.data_size)) { | 152 debug("GetFirmwareBody() failed for index %d\n", index); |
| 139 RSAPublicKeyFree(data_key); | 153 RSAPublicKeyFree(data_key); |
| 140 continue; | 154 continue; |
| 141 } | 155 } |
| 156 if (lfi->body_size_accum != preamble->body_signature.data_size) { |
| 157 debug("Hash updated %d bytes but expected %d\n", |
| 158 (int)lfi->body_size_accum, (int)preamble->body_signature.data_size); |
| 159 RSAPublicKeyFree(data_key); |
| 160 continue; |
| 161 } |
| 142 | 162 |
| 143 /* Verify firmware data */ | 163 /* Verify firmware data */ |
| 144 body_digest = DigestFinal(&lfi->body_digest_context); | 164 body_digest = DigestFinal(&lfi->body_digest_context); |
| 145 if (0 != VerifyDigest(body_digest, &preamble->body_signature, data_key)) { | 165 if (0 != VerifyDigest(body_digest, &preamble->body_signature, data_key)) { |
| 166 debug("Firmware body verification failed.\n"); |
| 146 RSAPublicKeyFree(data_key); | 167 RSAPublicKeyFree(data_key); |
| 147 Free(body_digest); | 168 Free(body_digest); |
| 148 continue; | 169 continue; |
| 149 } | 170 } |
| 150 | 171 |
| 151 /* Done with the digest and data key, so can free them now */ | 172 /* Done with the digest and data key, so can free them now */ |
| 152 RSAPublicKeyFree(data_key); | 173 RSAPublicKeyFree(data_key); |
| 153 Free(body_digest); | 174 Free(body_digest); |
| 154 | 175 |
| 155 /* If we're still here, the firmware is valid. */ | 176 /* If we're still here, the firmware is valid. */ |
| 177 debug("Firmware %d is valid.\n", index); |
| 156 if (-1 == good_index) { | 178 if (-1 == good_index) { |
| 157 VbPublicKey *kdest = (VbPublicKey*)params->kernel_sign_key_blob; | 179 VbPublicKey *kdest = (VbPublicKey*)params->kernel_sign_key_blob; |
| 158 | 180 |
| 159 /* Copy the kernel sign key blob into the destination buffer */ | 181 /* Copy the kernel sign key blob into the destination buffer */ |
| 160 PublicKeyInit(kdest, (uint8_t*)(kdest + 1), | 182 PublicKeyInit(kdest, (uint8_t*)(kdest + 1), |
| 161 (params->kernel_sign_key_size - sizeof(VbPublicKey))); | 183 (params->kernel_sign_key_size - sizeof(VbPublicKey))); |
| 162 | 184 |
| 163 if (0 != PublicKeyCopy(kdest, &preamble->kernel_subkey)) | 185 if (0 != PublicKeyCopy(kdest, &preamble->kernel_subkey)) { |
| 186 debug("Kernel subkey too big for buffer.\n"); |
| 164 continue; /* The firmware signature was good, but the public | 187 continue; /* The firmware signature was good, but the public |
| 165 * key was bigger that the caller can handle. */ | 188 * key was bigger that the caller can handle. */ |
| 189 } |
| 166 | 190 |
| 167 /* Save the key size we actually used */ | 191 /* Save the key size we actually used */ |
| 168 params->kernel_sign_key_size = kdest->key_offset + kdest->key_size; | 192 params->kernel_sign_key_size = kdest->key_offset + kdest->key_size; |
| 169 | 193 |
| 170 /* Save the good index, now that we're sure we can actually use | 194 /* Save the good index, now that we're sure we can actually use |
| 171 * this firmware. That's the one we'll boot. */ | 195 * this firmware. That's the one we'll boot. */ |
| 172 good_index = index; | 196 good_index = index; |
| 173 params->firmware_index = index; | 197 params->firmware_index = index; |
| 174 | 198 |
| 175 /* If the good firmware's key version is the same as the tpm, | 199 /* If the good firmware's key version is the same as the tpm, |
| (...skipping 12 matching lines...) Expand all Loading... |
| 188 | 212 |
| 189 /* Handle finding good firmware */ | 213 /* Handle finding good firmware */ |
| 190 if (good_index >= 0) { | 214 if (good_index >= 0) { |
| 191 | 215 |
| 192 /* Update TPM if necessary */ | 216 /* Update TPM if necessary */ |
| 193 if ((lowest_key_version > tpm_key_version) || | 217 if ((lowest_key_version > tpm_key_version) || |
| 194 (lowest_key_version == tpm_key_version && | 218 (lowest_key_version == tpm_key_version && |
| 195 lowest_fw_version > tpm_fw_version)) { | 219 lowest_fw_version > tpm_fw_version)) { |
| 196 if (0 != WriteStoredVersions(FIRMWARE_VERSIONS, | 220 if (0 != WriteStoredVersions(FIRMWARE_VERSIONS, |
| 197 (uint16_t)lowest_key_version, | 221 (uint16_t)lowest_key_version, |
| 198 (uint16_t)lowest_fw_version)) | 222 (uint16_t)lowest_fw_version)) { |
| 223 debug("Unable to write stored versions.\n"); |
| 199 return LOAD_FIRMWARE_RECOVERY; | 224 return LOAD_FIRMWARE_RECOVERY; |
| 225 } |
| 200 } | 226 } |
| 201 | 227 |
| 202 /* Lock Firmware TPM rollback indices from further writes. In | 228 /* Lock Firmware TPM rollback indices from further writes. In |
| 203 * this design, this is done by setting the globalLock bit, which | 229 * this design, this is done by setting the globalLock bit, which |
| 204 * is cleared only by TPM_Init at reboot. */ | 230 * is cleared only by TPM_Init at reboot. */ |
| 205 if (0 != LockFirmwareVersions()) | 231 if (0 != LockFirmwareVersions()) { |
| 232 debug("Unable to lock firmware versions.\n"); |
| 206 return LOAD_FIRMWARE_RECOVERY; | 233 return LOAD_FIRMWARE_RECOVERY; |
| 234 } |
| 207 | 235 |
| 208 /* Success */ | 236 /* Success */ |
| 237 debug("Will boot firmware index %d\n", (int)params->firmware_index); |
| 209 return LOAD_FIRMWARE_SUCCESS; | 238 return LOAD_FIRMWARE_SUCCESS; |
| 210 } | 239 } |
| 211 | 240 |
| 212 /* If we're still here, no good firmware, so go to recovery mode. */ | 241 /* If we're still here, no good firmware, so go to recovery mode. */ |
| 242 debug("Alas, no good firmware.\n"); |
| 213 return LOAD_FIRMWARE_RECOVERY; | 243 return LOAD_FIRMWARE_RECOVERY; |
| 214 } | 244 } |
| OLD | NEW |