event_log.c 8.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315
  1. /*
  2. * Copyright (c) 2020-2022, Arm Limited. All rights reserved.
  3. *
  4. * SPDX-License-Identifier: BSD-3-Clause
  5. */
  6. #include <assert.h>
  7. #include <errno.h>
  8. #include <string.h>
  9. #include <arch_helpers.h>
  10. #include <common/bl_common.h>
  11. #include <common/debug.h>
  12. #include <drivers/auth/crypto_mod.h>
  13. #include <drivers/measured_boot/event_log/event_log.h>
  14. #if TPM_ALG_ID == TPM_ALG_SHA512
  15. #define CRYPTO_MD_ID CRYPTO_MD_SHA512
  16. #elif TPM_ALG_ID == TPM_ALG_SHA384
  17. #define CRYPTO_MD_ID CRYPTO_MD_SHA384
  18. #elif TPM_ALG_ID == TPM_ALG_SHA256
  19. #define CRYPTO_MD_ID CRYPTO_MD_SHA256
  20. #else
  21. # error Invalid TPM algorithm.
  22. #endif /* TPM_ALG_ID */
  23. /* Running Event Log Pointer */
  24. static uint8_t *log_ptr;
  25. /* Pointer to the first byte past end of the Event Log buffer */
  26. static uintptr_t log_end;
  27. /* TCG_EfiSpecIdEvent */
  28. static const id_event_headers_t id_event_header = {
  29. .header = {
  30. .pcr_index = PCR_0,
  31. .event_type = EV_NO_ACTION,
  32. .digest = {0},
  33. .event_size = (uint32_t)(sizeof(id_event_struct_t) +
  34. (sizeof(id_event_algorithm_size_t) *
  35. HASH_ALG_COUNT))
  36. },
  37. .struct_header = {
  38. .signature = TCG_ID_EVENT_SIGNATURE_03,
  39. .platform_class = PLATFORM_CLASS_CLIENT,
  40. .spec_version_minor = TCG_SPEC_VERSION_MINOR_TPM2,
  41. .spec_version_major = TCG_SPEC_VERSION_MAJOR_TPM2,
  42. .spec_errata = TCG_SPEC_ERRATA_TPM2,
  43. .uintn_size = (uint8_t)(sizeof(unsigned int) /
  44. sizeof(uint32_t)),
  45. .number_of_algorithms = HASH_ALG_COUNT
  46. }
  47. };
  48. static const event2_header_t locality_event_header = {
  49. /*
  50. * All EV_NO_ACTION events SHALL set
  51. * TCG_PCR_EVENT2.pcrIndex = 0, unless otherwise specified
  52. */
  53. .pcr_index = PCR_0,
  54. /*
  55. * All EV_NO_ACTION events SHALL set
  56. * TCG_PCR_EVENT2.eventType = 03h
  57. */
  58. .event_type = EV_NO_ACTION,
  59. /*
  60. * All EV_NO_ACTION events SHALL set TCG_PCR_EVENT2.digests to all
  61. * 0x00's for each allocated Hash algorithm
  62. */
  63. .digests = {
  64. .count = HASH_ALG_COUNT
  65. }
  66. };
  67. /*
  68. * Record a measurement as a TCG_PCR_EVENT2 event
  69. *
  70. * @param[in] hash Pointer to hash data of TCG_DIGEST_SIZE bytes
  71. * @param[in] event_type Type of Event, Various Event Types are
  72. * mentioned in tcg.h header
  73. * @param[in] metadata_ptr Pointer to event_log_metadata_t structure
  74. *
  75. * There must be room for storing this new event into the event log buffer.
  76. */
  77. void event_log_record(const uint8_t *hash, uint32_t event_type,
  78. const event_log_metadata_t *metadata_ptr)
  79. {
  80. void *ptr = log_ptr;
  81. uint32_t name_len = 0U;
  82. assert(hash != NULL);
  83. assert(metadata_ptr != NULL);
  84. /* event_log_buf_init() must have been called prior to this. */
  85. assert(log_ptr != NULL);
  86. if (metadata_ptr->name != NULL) {
  87. name_len = (uint32_t)strlen(metadata_ptr->name) + 1U;
  88. }
  89. /* Check for space in Event Log buffer */
  90. assert(((uintptr_t)ptr + (uint32_t)EVENT2_HDR_SIZE + name_len) <
  91. log_end);
  92. /*
  93. * As per TCG specifications, firmware components that are measured
  94. * into PCR[0] must be logged in the event log using the event type
  95. * EV_POST_CODE.
  96. */
  97. /* TCG_PCR_EVENT2.PCRIndex */
  98. ((event2_header_t *)ptr)->pcr_index = metadata_ptr->pcr;
  99. /* TCG_PCR_EVENT2.EventType */
  100. ((event2_header_t *)ptr)->event_type = event_type;
  101. /* TCG_PCR_EVENT2.Digests.Count */
  102. ptr = (uint8_t *)ptr + offsetof(event2_header_t, digests);
  103. ((tpml_digest_values *)ptr)->count = HASH_ALG_COUNT;
  104. /* TCG_PCR_EVENT2.Digests[] */
  105. ptr = (uint8_t *)((uintptr_t)ptr +
  106. offsetof(tpml_digest_values, digests));
  107. /* TCG_PCR_EVENT2.Digests[].AlgorithmId */
  108. ((tpmt_ha *)ptr)->algorithm_id = TPM_ALG_ID;
  109. /* TCG_PCR_EVENT2.Digests[].Digest[] */
  110. ptr = (uint8_t *)((uintptr_t)ptr + offsetof(tpmt_ha, digest));
  111. /* Copy digest */
  112. (void)memcpy(ptr, (const void *)hash, TCG_DIGEST_SIZE);
  113. /* TCG_PCR_EVENT2.EventSize */
  114. ptr = (uint8_t *)((uintptr_t)ptr + TCG_DIGEST_SIZE);
  115. ((event2_data_t *)ptr)->event_size = name_len;
  116. /* Copy event data to TCG_PCR_EVENT2.Event */
  117. if (metadata_ptr->name != NULL) {
  118. (void)memcpy((void *)(((event2_data_t *)ptr)->event),
  119. (const void *)metadata_ptr->name, name_len);
  120. }
  121. /* End of event data */
  122. log_ptr = (uint8_t *)((uintptr_t)ptr +
  123. offsetof(event2_data_t, event) + name_len);
  124. }
  125. void event_log_buf_init(uint8_t *event_log_start, uint8_t *event_log_finish)
  126. {
  127. assert(event_log_start != NULL);
  128. assert(event_log_finish > event_log_start);
  129. log_ptr = event_log_start;
  130. log_end = (uintptr_t)event_log_finish;
  131. }
  132. /*
  133. * Initialise Event Log global variables, used during the recording
  134. * of various payload measurements into the Event Log buffer
  135. *
  136. * @param[in] event_log_start Base address of Event Log buffer
  137. * @param[in] event_log_finish End address of Event Log buffer,
  138. * it is a first byte past end of the
  139. * buffer
  140. */
  141. void event_log_init(uint8_t *event_log_start, uint8_t *event_log_finish)
  142. {
  143. event_log_buf_init(event_log_start, event_log_finish);
  144. }
  145. void event_log_write_specid_event(void)
  146. {
  147. void *ptr = log_ptr;
  148. /* event_log_buf_init() must have been called prior to this. */
  149. assert(log_ptr != NULL);
  150. assert(((uintptr_t)log_ptr + ID_EVENT_SIZE) < log_end);
  151. /*
  152. * Add Specification ID Event first
  153. *
  154. * Copy TCG_EfiSpecIDEventStruct structure header
  155. */
  156. (void)memcpy(ptr, (const void *)&id_event_header,
  157. sizeof(id_event_header));
  158. ptr = (uint8_t *)((uintptr_t)ptr + sizeof(id_event_header));
  159. /* TCG_EfiSpecIdEventAlgorithmSize structure */
  160. ((id_event_algorithm_size_t *)ptr)->algorithm_id = TPM_ALG_ID;
  161. ((id_event_algorithm_size_t *)ptr)->digest_size = TCG_DIGEST_SIZE;
  162. ptr = (uint8_t *)((uintptr_t)ptr + sizeof(id_event_algorithm_size_t));
  163. /*
  164. * TCG_EfiSpecIDEventStruct.vendorInfoSize
  165. * No vendor data
  166. */
  167. ((id_event_struct_data_t *)ptr)->vendor_info_size = 0;
  168. log_ptr = (uint8_t *)((uintptr_t)ptr +
  169. offsetof(id_event_struct_data_t, vendor_info));
  170. }
  171. /*
  172. * Initialises Event Log by writing Specification ID and
  173. * Startup Locality events
  174. */
  175. void event_log_write_header(void)
  176. {
  177. const char locality_signature[] = TCG_STARTUP_LOCALITY_SIGNATURE;
  178. void *ptr;
  179. event_log_write_specid_event();
  180. ptr = log_ptr;
  181. assert(((uintptr_t)log_ptr + LOC_EVENT_SIZE) < log_end);
  182. /*
  183. * The Startup Locality event should be placed in the log before
  184. * any event which extends PCR[0].
  185. *
  186. * Ref. TCG PC Client Platform Firmware Profile 9.4.5.3
  187. */
  188. /* Copy Startup Locality Event Header */
  189. (void)memcpy(ptr, (const void *)&locality_event_header,
  190. sizeof(locality_event_header));
  191. ptr = (uint8_t *)((uintptr_t)ptr + sizeof(locality_event_header));
  192. /* TCG_PCR_EVENT2.Digests[].AlgorithmId */
  193. ((tpmt_ha *)ptr)->algorithm_id = TPM_ALG_ID;
  194. /* TCG_PCR_EVENT2.Digests[].Digest[] */
  195. (void)memset(&((tpmt_ha *)ptr)->digest, 0, TCG_DIGEST_SIZE);
  196. ptr = (uint8_t *)((uintptr_t)ptr +
  197. offsetof(tpmt_ha, digest) + TCG_DIGEST_SIZE);
  198. /* TCG_PCR_EVENT2.EventSize */
  199. ((event2_data_t *)ptr)->event_size =
  200. (uint32_t)sizeof(startup_locality_event_t);
  201. ptr = (uint8_t *)((uintptr_t)ptr + offsetof(event2_data_t, event));
  202. /* TCG_EfiStartupLocalityEvent.Signature */
  203. (void)memcpy(ptr, (const void *)locality_signature,
  204. sizeof(TCG_STARTUP_LOCALITY_SIGNATURE));
  205. /*
  206. * TCG_EfiStartupLocalityEvent.StartupLocality = 0:
  207. * the platform's boot firmware
  208. */
  209. ((startup_locality_event_t *)ptr)->startup_locality = 0U;
  210. log_ptr = (uint8_t *)((uintptr_t)ptr + sizeof(startup_locality_event_t));
  211. }
  212. int event_log_measure(uintptr_t data_base, uint32_t data_size,
  213. unsigned char hash_data[CRYPTO_MD_MAX_SIZE])
  214. {
  215. /* Calculate hash */
  216. return crypto_mod_calc_hash(CRYPTO_MD_ID,
  217. (void *)data_base, data_size, hash_data);
  218. }
  219. /*
  220. * Calculate and write hash of image, configuration data, etc.
  221. * to Event Log.
  222. *
  223. * @param[in] data_base Address of data
  224. * @param[in] data_size Size of data
  225. * @param[in] data_id Data ID
  226. * @param[in] metadata_ptr Event Log metadata
  227. * @return:
  228. * 0 = success
  229. * < 0 = error
  230. */
  231. int event_log_measure_and_record(uintptr_t data_base, uint32_t data_size,
  232. uint32_t data_id,
  233. const event_log_metadata_t *metadata_ptr)
  234. {
  235. unsigned char hash_data[CRYPTO_MD_MAX_SIZE];
  236. int rc;
  237. assert(metadata_ptr != NULL);
  238. /* Get the metadata associated with this image. */
  239. while ((metadata_ptr->id != EVLOG_INVALID_ID) &&
  240. (metadata_ptr->id != data_id)) {
  241. metadata_ptr++;
  242. }
  243. assert(metadata_ptr->id != EVLOG_INVALID_ID);
  244. /* Measure the payload with algorithm selected by EventLog driver */
  245. rc = event_log_measure(data_base, data_size, hash_data);
  246. if (rc != 0) {
  247. return rc;
  248. }
  249. event_log_record(hash_data, EV_POST_CODE, metadata_ptr);
  250. return 0;
  251. }
  252. /*
  253. * Get current Event Log buffer size i.e. used space of Event Log buffer
  254. *
  255. * @param[in] event_log_start Base Pointer to Event Log buffer
  256. *
  257. * @return: current Size of Event Log buffer
  258. */
  259. size_t event_log_get_cur_size(uint8_t *event_log_start)
  260. {
  261. assert(event_log_start != NULL);
  262. assert(log_ptr >= event_log_start);
  263. return (size_t)((uintptr_t)log_ptr - (uintptr_t)event_log_start);
  264. }