blob: 08ec179346e29d0dd3cb7da44b25b34d82e05a77 [file] [log] [blame]
Simon Glass66262ed2020-02-06 09:55:04 -07001// SPDX-License-Identifier: GPL-2.0
2/*
3 * Cr50 / H1 TPM support
4 *
5 * Copyright 2018 Google LLC
6 */
7
8#define LOG_CATEGORY UCLASS_TPM
9
Simon Glass66262ed2020-02-06 09:55:04 -070010#include <dm.h>
11#include <i2c.h>
12#include <irq.h>
Simon Glass0f2af882020-05-10 11:40:05 -060013#include <log.h>
Simon Glass66262ed2020-02-06 09:55:04 -070014#include <spl.h>
Tom Rinidec7ea02024-05-20 13:35:03 -060015#include <time.h>
Simon Glass3f7a73a2022-08-30 21:05:37 -060016#include <tpm-common.h>
Simon Glass66262ed2020-02-06 09:55:04 -070017#include <tpm-v2.h>
Simon Glass11b1a272020-09-22 12:45:24 -060018#include <acpi/acpigen.h>
19#include <acpi/acpi_device.h>
Simon Glass66262ed2020-02-06 09:55:04 -070020#include <asm/gpio.h>
21#include <asm/io.h>
Simon Glass3f7a73a2022-08-30 21:05:37 -060022#include <asm/unaligned.h>
Simon Glassdbd79542020-05-10 11:40:11 -060023#include <linux/delay.h>
Simon Glass11b1a272020-09-22 12:45:24 -060024#include <dm/acpi.h>
Simon Glass66262ed2020-02-06 09:55:04 -070025
26enum {
27 TIMEOUT_INIT_MS = 30000, /* Very long timeout for TPM init */
28 TIMEOUT_LONG_US = 2 * 1000 * 1000,
29 TIMEOUT_SHORT_US = 2 * 1000,
30 TIMEOUT_NO_IRQ_US = 20 * 1000,
31 TIMEOUT_IRQ_US = 100 * 1000,
32};
33
34enum {
35 CR50_DID_VID = 0x00281ae0L
36};
37
38enum {
39 CR50_MAX_BUF_SIZE = 63,
40};
41
Simon Glass3f7a73a2022-08-30 21:05:37 -060042/*
43 * Operations specific to the Cr50 TPM used on Chromium OS and Android devices
44 *
45 * FIXME: below is not enough to differentiate between vendors commands
46 * of numerous devices. However, the current tpm2 APIs aren't very amenable
47 * to extending generically because the marshaling code is assuming all
48 * knowledge of all commands.
49 */
50#define TPM2_CC_VENDOR_BIT_MASK 0x20000000
51
52#define TPM2_CR50_VENDOR_COMMAND (TPM2_CC_VENDOR_BIT_MASK | 0)
53#define TPM2_CR50_SUB_CMD_IMMEDIATE_RESET 19
54#define TPM2_CR50_SUB_CMD_NVMEM_ENABLE_COMMITS 21
55#define TPM2_CR50_SUB_CMD_REPORT_TPM_STATE 23
56#define TPM2_CR50_SUB_CMD_TURN_UPDATE_ON 24
57#define TPM2_CR50_SUB_CMD_GET_REC_BTN 29
58#define TPM2_CR50_SUB_CMD_TPM_MODE 40
59#define TPM2_CR50_SUB_CMD_GET_BOOT_MODE 52
60#define TPM2_CR50_SUB_CMD_RESET_EC 53
61
62/* Cr50 vendor-specific error codes. */
63#define VENDOR_RC_ERR 0x00000500
64enum cr50_vendor_rc {
65 VENDOR_RC_INTERNAL_ERROR = (VENDOR_RC_ERR | 6),
66 VENDOR_RC_NO_SUCH_SUBCOMMAND = (VENDOR_RC_ERR | 8),
67 VENDOR_RC_NO_SUCH_COMMAND = (VENDOR_RC_ERR | 127),
68};
69
70enum cr50_tpm_mode {
71 /*
72 * Default state: TPM is enabled, and may be set to either
73 * TPM_MODE_ENABLED or TPM_MODE_DISABLED.
74 */
75 TPM_MODE_ENABLED_TENTATIVE = 0,
76
77 /* TPM is enabled, and mode may not be changed. */
78 TPM_MODE_ENABLED = 1,
79
80 /* TPM is disabled, and mode may not be changed. */
81 TPM_MODE_DISABLED = 2,
82
83 TPM_MODE_INVALID,
84};
85
Simon Glass2c161252020-04-08 16:57:23 -060086/**
87 * struct cr50_priv - Private driver data
88 *
89 * @ready_gpio: GPIO to use to check if the TPM is ready
90 * @irq: IRQ to use check if the TPM is ready (has priority over @ready_gpio)
91 * @locality: Currenttly claimed locality (-1 if none)
92 * @vendor: vendor: Vendor ID for TPM
93 * @use_irq: true to use @irq, false to use @ready if available
94 */
Simon Glass66262ed2020-02-06 09:55:04 -070095struct cr50_priv {
96 struct gpio_desc ready_gpio;
97 struct irq irq;
98 int locality;
99 uint vendor;
100 bool use_irq;
101};
102
Simon Glass3f7a73a2022-08-30 21:05:37 -0600103/*
104 * The below structure represents the body of the response to the 'report tpm
105 * state' vendor command.
106 *
107 * It is transferred over the wire, so it needs to be serialized/deserialized,
108 * and it is likely to change, so its contents must be versioned.
109 */
110#define TPM_STATE_VERSION 1
111struct tpm_vendor_state {
112 u32 version;
113 /*
114 * The following three fields are set by the TPM in case of an assert.
115 * There is no other processing than setting the source code line
116 * number, error code and the first 4 characters of the function name.
117 *
118 * We don't expect this happening, but it is included in the report
119 * just in case.
120 */
121 u32 fail_line; /* s_failLIne */
122 u32 fail_code; /* s_failCode */
123 char func_name[4]; /* s_failFunction, limited to 4 chars */
124
125 /*
126 * The following two fields are the current time filtered value of the
127 * 'failed tries' TPM counter, and the maximum allowed value of the
128 * counter.
129 *
130 * failed_tries == max_tries is the definition of the TPM lockout
131 * condition.
132 */
133 u32 failed_tries; /* gp.failedTries */
134 u32 max_tries; /* gp.maxTries */
135 /* The below fields are present in version 2 and above */
136};
137
Simon Glass66262ed2020-02-06 09:55:04 -0700138/* Wait for interrupt to indicate TPM is ready */
139static int cr50_i2c_wait_tpm_ready(struct udevice *dev)
140{
141 struct cr50_priv *priv = dev_get_priv(dev);
142 ulong timeout, base;
143 int i;
144
145 if (!priv->use_irq && !dm_gpio_is_valid(&priv->ready_gpio)) {
146 /* Fixed delay if interrupt not supported */
147 udelay(TIMEOUT_NO_IRQ_US);
148 return 0;
149 }
150
151 base = timer_get_us();
152 timeout = base + TIMEOUT_IRQ_US;
153
154 i = 0;
155 while (priv->use_irq ? !irq_read_and_clear(&priv->irq) :
156 !dm_gpio_get_value(&priv->ready_gpio)) {
157 i++;
158 if ((int)(timer_get_us() - timeout) >= 0) {
159 log_warning("Timeout\n");
160 /* Use this instead of the -ETIMEDOUT used by i2c */
161 return -ETIME;
162 }
163 }
164 log_debug("i=%d\n", i);
165
166 return 0;
167}
168
169/* Clear pending interrupts */
170static void cr50_i2c_clear_tpm_irq(struct udevice *dev)
171{
172 struct cr50_priv *priv = dev_get_priv(dev);
173
174 if (priv->use_irq)
175 irq_read_and_clear(&priv->irq);
176}
177
178/*
179 * cr50_i2c_read() - read from TPM register
180 *
181 * @dev: TPM chip information
182 * @addr: register address to read from
183 * @buffer: provided by caller
184 * @len: number of bytes to read
185 *
186 * 1) send register address byte 'addr' to the TPM
187 * 2) wait for TPM to indicate it is ready
188 * 3) read 'len' bytes of TPM response into the provided 'buffer'
189 *
190 * Return 0 on success. -ve on error
191 */
192static int cr50_i2c_read(struct udevice *dev, u8 addr, u8 *buffer,
193 size_t len)
194{
195 int ret;
196
197 /* Clear interrupt before starting transaction */
198 cr50_i2c_clear_tpm_irq(dev);
199
200 /* Send the register address byte to the TPM */
201 ret = dm_i2c_write(dev, 0, &addr, 1);
202 if (ret) {
203 log_err("Address write failed (err=%d)\n", ret);
204 return ret;
205 }
206
207 /* Wait for TPM to be ready with response data */
208 ret = cr50_i2c_wait_tpm_ready(dev);
209 if (ret)
210 return ret;
211
212 /* Read response data frrom the TPM */
213 ret = dm_i2c_read(dev, 0, buffer, len);
214 if (ret) {
215 log_err("Read response failed (err=%d)\n", ret);
216 return ret;
217 }
218
219 return 0;
220}
221
222/*
223 * cr50_i2c_write() - write to TPM register
224 *
225 * @dev: TPM chip information
226 * @addr: register address to write to
227 * @buffer: data to write
228 * @len: number of bytes to write
229 *
230 * 1) prepend the provided address to the provided data
231 * 2) send the address+data to the TPM
232 * 3) wait for TPM to indicate it is done writing
233 *
234 * Returns -1 on error, 0 on success.
235 */
236static int cr50_i2c_write(struct udevice *dev, u8 addr, const u8 *buffer,
237 size_t len)
238{
239 u8 buf[len + 1];
240 int ret;
241
242 if (len > CR50_MAX_BUF_SIZE) {
243 log_err("Length %zd is too large\n", len);
244 return -E2BIG;
245 }
246
247 /* Prepend the 'register address' to the buffer */
248 buf[0] = addr;
249 memcpy(buf + 1, buffer, len);
250
251 /* Clear interrupt before starting transaction */
252 cr50_i2c_clear_tpm_irq(dev);
253
254 /* Send write request buffer with address */
255 ret = dm_i2c_write(dev, 0, buf, len + 1);
256 if (ret) {
257 log_err("Error writing to TPM (err=%d)\n", ret);
258 return ret;
259 }
260
261 /* Wait for TPM to be ready */
262 return cr50_i2c_wait_tpm_ready(dev);
263}
264
Simon Glassf6155cf2020-12-31 09:52:12 -0700265static inline u8 tpm_access(int locality)
Simon Glass66262ed2020-02-06 09:55:04 -0700266{
Simon Glassf6155cf2020-12-31 09:52:12 -0700267 if (locality == -1)
268 locality = 0;
Simon Glass66262ed2020-02-06 09:55:04 -0700269 return 0x0 | (locality << 4);
270}
271
Simon Glassf6155cf2020-12-31 09:52:12 -0700272static inline u8 tpm_sts(int locality)
Simon Glass66262ed2020-02-06 09:55:04 -0700273{
Simon Glassf6155cf2020-12-31 09:52:12 -0700274 if (locality == -1)
275 locality = 0;
Simon Glass66262ed2020-02-06 09:55:04 -0700276 return 0x1 | (locality << 4);
277}
278
Simon Glassf6155cf2020-12-31 09:52:12 -0700279static inline u8 tpm_data_fifo(int locality)
Simon Glass66262ed2020-02-06 09:55:04 -0700280{
Simon Glassf6155cf2020-12-31 09:52:12 -0700281 if (locality == -1)
282 locality = 0;
Simon Glass66262ed2020-02-06 09:55:04 -0700283 return 0x5 | (locality << 4);
284}
285
Simon Glassf6155cf2020-12-31 09:52:12 -0700286static inline u8 tpm_did_vid(int locality)
Simon Glass66262ed2020-02-06 09:55:04 -0700287{
Simon Glassf6155cf2020-12-31 09:52:12 -0700288 if (locality == -1)
289 locality = 0;
Simon Glass66262ed2020-02-06 09:55:04 -0700290 return 0x6 | (locality << 4);
291}
292
293static int release_locality(struct udevice *dev, int force)
294{
295 struct cr50_priv *priv = dev_get_priv(dev);
296 u8 mask = TPM_ACCESS_VALID | TPM_ACCESS_REQUEST_PENDING;
297 u8 addr = tpm_access(priv->locality);
298 int ret;
299 u8 buf;
300
301 ret = cr50_i2c_read(dev, addr, &buf, 1);
302 if (ret)
303 return ret;
304
305 if (force || (buf & mask) == mask) {
306 buf = TPM_ACCESS_ACTIVE_LOCALITY;
307 cr50_i2c_write(dev, addr, &buf, 1);
308 }
309
Simon Glassfec444c2020-04-08 16:57:22 -0600310 priv->locality = -1;
Simon Glass66262ed2020-02-06 09:55:04 -0700311
312 return 0;
313}
314
315/* cr50 requires all 4 bytes of status register to be read */
316static int cr50_i2c_status(struct udevice *dev)
317{
318 struct cr50_priv *priv = dev_get_priv(dev);
319 u8 buf[4];
320 int ret;
321
322 ret = cr50_i2c_read(dev, tpm_sts(priv->locality), buf, sizeof(buf));
323 if (ret) {
324 log_warning("%s: Failed to read status\n", __func__);
325 return ret;
326 }
327
328 return buf[0];
329}
330
331/* cr50 requires all 4 bytes of status register to be written */
332static int cr50_i2c_ready(struct udevice *dev)
333{
334 struct cr50_priv *priv = dev_get_priv(dev);
335 u8 buf[4] = { TPM_STS_COMMAND_READY };
336 int ret;
337
338 ret = cr50_i2c_write(dev, tpm_sts(priv->locality), buf, sizeof(buf));
339 if (ret)
340 return ret;
341
342 udelay(TIMEOUT_SHORT_US);
343
344 return 0;
345}
346
347static int cr50_i2c_wait_burststs(struct udevice *dev, u8 mask,
348 size_t *burst, int *status)
349{
350 struct cr50_priv *priv = dev_get_priv(dev);
351 ulong timeout;
352 u32 buf;
353
354 /*
355 * cr50 uses bytes 3:2 of status register for burst count and all 4
356 * bytes must be read
357 */
358 timeout = timer_get_us() + TIMEOUT_LONG_US;
359 while (timer_get_us() < timeout) {
360 if (cr50_i2c_read(dev, tpm_sts(priv->locality),
361 (u8 *)&buf, sizeof(buf)) < 0) {
362 udelay(TIMEOUT_SHORT_US);
363 continue;
364 }
365
366 *status = buf & 0xff;
367 *burst = le16_to_cpu((buf >> 8) & 0xffff);
368
369 if ((*status & mask) == mask &&
370 *burst > 0 && *burst <= CR50_MAX_BUF_SIZE)
371 return 0;
372
373 udelay(TIMEOUT_SHORT_US);
374 }
375
376 log_warning("Timeout reading burst and status\n");
377
378 return -ETIMEDOUT;
379}
380
381static int cr50_i2c_recv(struct udevice *dev, u8 *buf, size_t buf_len)
382{
383 struct cr50_priv *priv = dev_get_priv(dev);
384 size_t burstcnt, expected, current, len;
385 u8 addr = tpm_data_fifo(priv->locality);
386 u8 mask = TPM_STS_VALID | TPM_STS_DATA_AVAIL;
387 u32 expected_buf;
388 int status;
389 int ret;
390
Simon Glass7ec382a2021-02-06 14:23:32 -0700391 log_debug("%s: buf_len=%x\n", __func__, buf_len);
Simon Glass66262ed2020-02-06 09:55:04 -0700392 if (buf_len < TPM_HEADER_SIZE)
393 return -E2BIG;
394
395 ret = cr50_i2c_wait_burststs(dev, mask, &burstcnt, &status);
396 if (ret < 0) {
397 log_warning("First chunk not available\n");
398 goto out_err;
399 }
400
401 /* Read first chunk of burstcnt bytes */
402 if (cr50_i2c_read(dev, addr, buf, burstcnt) < 0) {
403 log_warning("Read failed\n");
404 goto out_err;
405 }
406
407 /* Determine expected data in the return buffer */
408 memcpy(&expected_buf, buf + TPM_CMD_COUNT_OFFSET, sizeof(expected_buf));
409 expected = be32_to_cpu(expected_buf);
410 if (expected > buf_len) {
411 log_warning("Too much data: %zu > %zu\n", expected, buf_len);
412 goto out_err;
413 }
414
415 /* Now read the rest of the data */
416 current = burstcnt;
417 while (current < expected) {
418 /* Read updated burst count and check status */
419 if (cr50_i2c_wait_burststs(dev, mask, &burstcnt, &status) < 0) {
420 log_warning("- burst failure1\n");
421 goto out_err;
422 }
423
424 len = min(burstcnt, expected - current);
425 if (cr50_i2c_read(dev, addr, buf + current, len) != 0) {
426 log_warning("Read failed\n");
427 goto out_err;
428 }
429
430 current += len;
431 }
432
433 if (cr50_i2c_wait_burststs(dev, TPM_STS_VALID, &burstcnt,
434 &status) < 0) {
435 log_warning("- burst failure2\n");
436 goto out_err;
437 }
438 if (status & TPM_STS_DATA_AVAIL) {
439 log_warning("Data still available\n");
440 goto out_err;
441 }
442
443 return current;
444
445out_err:
446 /* Abort current transaction if still pending */
447 ret = cr50_i2c_status(dev);
448 if (ret < 0)
449 return ret;
450 if (ret & TPM_STS_COMMAND_READY) {
451 ret = cr50_i2c_ready(dev);
452 if (ret)
453 return ret;
454 }
455
456 return -EIO;
457}
458
459static int cr50_i2c_send(struct udevice *dev, const u8 *buf, size_t len)
460{
461 struct cr50_priv *priv = dev_get_priv(dev);
Simon Glass66262ed2020-02-06 09:55:04 -0700462 int status;
463 size_t burstcnt, limit, sent = 0;
464 u8 tpm_go[4] = { TPM_STS_GO };
465 ulong timeout;
466 int ret;
467
Simon Glass7ec382a2021-02-06 14:23:32 -0700468 log_debug("len=%x\n", len);
Simon Glass66262ed2020-02-06 09:55:04 -0700469 timeout = timer_get_us() + TIMEOUT_LONG_US;
470 do {
471 ret = cr50_i2c_status(dev);
472 if (ret < 0)
473 goto out_err;
474 if (ret & TPM_STS_COMMAND_READY)
475 break;
476
477 if (timer_get_us() > timeout)
478 goto out_err;
479
480 ret = cr50_i2c_ready(dev);
481 if (ret)
482 goto out_err;
483 } while (1);
484
485 while (len > 0) {
486 u8 mask = TPM_STS_VALID;
487
488 /* Wait for data if this is not the first chunk */
489 if (sent > 0)
490 mask |= TPM_STS_DATA_EXPECT;
491
492 if (cr50_i2c_wait_burststs(dev, mask, &burstcnt, &status) < 0)
493 goto out_err;
494
495 /*
496 * Use burstcnt - 1 to account for the address byte
497 * that is inserted by cr50_i2c_write()
498 */
499 limit = min(burstcnt - 1, len);
500 if (cr50_i2c_write(dev, tpm_data_fifo(priv->locality),
501 &buf[sent], limit) != 0) {
502 log_warning("Write failed\n");
503 goto out_err;
504 }
505
506 sent += limit;
507 len -= limit;
508 }
509
510 /* Ensure TPM is not expecting more data */
511 if (cr50_i2c_wait_burststs(dev, TPM_STS_VALID, &burstcnt, &status) < 0)
512 goto out_err;
513 if (status & TPM_STS_DATA_EXPECT) {
514 log_warning("Data still expected\n");
515 goto out_err;
516 }
517
518 /* Start the TPM command */
519 ret = cr50_i2c_write(dev, tpm_sts(priv->locality), tpm_go,
520 sizeof(tpm_go));
521 if (ret) {
522 log_warning("Start command failed\n");
523 goto out_err;
524 }
525
526 return sent;
527
528out_err:
529 /* Abort current transaction if still pending */
530 ret = cr50_i2c_status(dev);
531
532 if (ret < 0 || (ret & TPM_STS_COMMAND_READY)) {
533 ret = cr50_i2c_ready(dev);
534 if (ret)
535 return ret;
536 }
537
538 return -EIO;
539}
540
541/**
542 * process_reset() - Wait for the Cr50 to reset
543 *
544 * Cr50 processes reset requests asynchronously and conceivably could be busy
545 * executing a long command and not reacting to the reset pulse for a while.
546 *
547 * This function will make sure that the AP does not proceed with boot until
548 * TPM finished reset processing.
549 *
550 * @dev: Cr50 device
Heinrich Schuchardt47b4c022022-01-19 18:05:50 +0100551 * Return: 0 if OK, -EPERM if locality could not be taken
Simon Glass66262ed2020-02-06 09:55:04 -0700552 */
553static int process_reset(struct udevice *dev)
554{
555 const int loc = 0;
556 u8 access;
557 ulong start;
558
559 /*
560 * Locality is released by TPM reset.
561 *
562 * If locality is taken at this point, this could be due to the fact
563 * that the TPM is performing a long operation and has not processed
564 * reset request yet. We'll wait up to CR50_TIMEOUT_INIT_MS and see if
565 * it releases locality when reset is processed.
566 */
567 start = get_timer(0);
568 do {
569 const u8 mask = TPM_ACCESS_VALID | TPM_ACCESS_ACTIVE_LOCALITY;
570 int ret;
571
572 ret = cr50_i2c_read(dev, tpm_access(loc),
573 &access, sizeof(access));
574 if (ret || ((access & mask) == mask)) {
575 /*
576 * Don't bombard the chip with traffic; let it keep
577 * processing the command.
578 */
579 mdelay(2);
580 continue;
581 }
582
Simon Glass5726f2f2020-09-27 18:46:24 -0600583 log_debug("TPM ready after %ld ms\n", get_timer(start));
Simon Glass66262ed2020-02-06 09:55:04 -0700584
585 return 0;
586 } while (get_timer(start) < TIMEOUT_INIT_MS);
587
Simon Glass5726f2f2020-09-27 18:46:24 -0600588 log_err("TPM failed to reset after %ld ms, status: %#x\n",
589 get_timer(start), access);
Simon Glass66262ed2020-02-06 09:55:04 -0700590
591 return -EPERM;
592}
593
594/*
595 * Locality could be already claimed (if this is a later U-Boot phase and the
596 * read-only U-Boot did not release it), or not yet claimed, if this is TPL or
597 * the older read-only U-Boot did release it.
598 */
599static int claim_locality(struct udevice *dev, int loc)
600{
601 const u8 mask = TPM_ACCESS_VALID | TPM_ACCESS_ACTIVE_LOCALITY;
Simon Glassfec444c2020-04-08 16:57:22 -0600602 struct cr50_priv *priv = dev_get_priv(dev);
Simon Glass66262ed2020-02-06 09:55:04 -0700603 u8 access;
604 int ret;
605
606 ret = cr50_i2c_read(dev, tpm_access(loc), &access, sizeof(access));
607 if (ret)
608 return log_msg_ret("read1", ret);
609
610 if ((access & mask) == mask) {
611 log_warning("Locality already claimed\n");
612 return 0;
613 }
614
615 access = TPM_ACCESS_REQUEST_USE;
616 ret = cr50_i2c_write(dev, tpm_access(loc), &access, sizeof(access));
617 if (ret)
618 return log_msg_ret("write", ret);
619
620 ret = cr50_i2c_read(dev, tpm_access(loc), &access, sizeof(access));
621 if (ret)
622 return log_msg_ret("read2", ret);
623
624 if ((access & mask) != mask) {
625 log_err("Failed to claim locality\n");
626 return -EPERM;
627 }
Simon Glass5726f2f2020-09-27 18:46:24 -0600628 log_debug("Claimed locality %d\n", loc);
Simon Glassfec444c2020-04-08 16:57:22 -0600629 priv->locality = loc;
Simon Glass66262ed2020-02-06 09:55:04 -0700630
631 return 0;
632}
633
634static int cr50_i2c_get_desc(struct udevice *dev, char *buf, int size)
635{
Simon Glass71fa5b42020-12-03 16:55:18 -0700636 struct dm_i2c_chip *chip = dev_get_parent_plat(dev);
Simon Glass66262ed2020-02-06 09:55:04 -0700637 struct cr50_priv *priv = dev_get_priv(dev);
Simon Glass8e5f3452020-12-31 09:52:13 -0700638 int len;
639
640 len = snprintf(buf, size, "cr50 TPM 2.0 (i2c %02x id %x), ",
641 chip->chip_addr, priv->vendor >> 16);
642 if (priv->use_irq) {
643 len += snprintf(buf + len, size - len, "irq=%s/%ld",
644 priv->irq.dev->name, priv->irq.id);
645 } else if (dm_gpio_is_valid(&priv->ready_gpio)) {
646 len += snprintf(buf + len, size - len, "gpio=%s/%u",
647 priv->ready_gpio.dev->name,
648 priv->ready_gpio.offset);
649 } else {
650 len += snprintf(buf + len, size - len, "delay=%d",
651 TIMEOUT_NO_IRQ_US);
652 }
Simon Glass66262ed2020-02-06 09:55:04 -0700653
Simon Glass8e5f3452020-12-31 09:52:13 -0700654 return len;
Simon Glass66262ed2020-02-06 09:55:04 -0700655}
656
Simon Glass3f7a73a2022-08-30 21:05:37 -0600657static int stringify_state(char *buf, int len, char *str, size_t max_size)
658{
659 struct tpm_vendor_state state;
660 size_t text_size = 0;
661
662 state.version = get_unaligned_be32(buf +
663 offsetof(struct tpm_vendor_state, version));
664 state.fail_line = get_unaligned_be32(buf +
665 offsetof(struct tpm_vendor_state, fail_line));
666 state.fail_code = get_unaligned_be32(buf +
667 offsetof(struct tpm_vendor_state, fail_code));
668 memcpy(state.func_name,
669 buf + offsetof(struct tpm_vendor_state, func_name),
670 sizeof(state.func_name));
671 state.failed_tries = get_unaligned_be32(buf +
672 offsetof(struct tpm_vendor_state, failed_tries));
673 state.max_tries = get_unaligned_be32(buf +
674 offsetof(struct tpm_vendor_state, max_tries));
675
676 text_size += snprintf(str + text_size, max_size - text_size,
677 "v=%d", state.version);
678 if (text_size >= max_size)
679 return -ENOSPC;
680
681 if (state.version > TPM_STATE_VERSION)
682 text_size += snprintf(str + text_size,
683 max_size - text_size,
684 " not fully supported\n");
685 if (text_size >= max_size)
686 return -ENOSPC;
687
688 if (state.version == 0)
689 return -EINVAL; /* This should never happen */
690
691 text_size += snprintf(str + text_size,
692 max_size - text_size,
693 " failed_tries=%d max_tries=%d\n",
694 state.failed_tries, state.max_tries);
695 if (text_size >= max_size)
696 return -ENOSPC;
697
698 if (state.fail_line) {
699 /* make sure function name is zero terminated. */
700 char func_name[sizeof(state.func_name) + 1];
701
702 memcpy(func_name, state.func_name, sizeof(state.func_name));
703 func_name[sizeof(state.func_name)] = '\0';
704
705 text_size += snprintf(str + text_size,
706 max_size - text_size,
707 "tpm failed: f %s line %d code %d",
708 func_name,
709 state.fail_line,
710 state.fail_code);
711 if (text_size >= max_size)
712 return -ENOSPC;
713 }
714
715 return 0;
716}
717
718static int cr50_i2c_report_state(struct udevice *dev, char *str, int str_max)
719{
720 char buf[50];
721 size_t buf_size = sizeof(buf);
722 int ret;
723
724 ret = tpm2_report_state(dev, TPM2_CR50_VENDOR_COMMAND,
725 TPM2_CR50_SUB_CMD_REPORT_TPM_STATE,
726 buf, &buf_size);
727 if (ret)
728 return ret;
729
730 /* TPM responded as expected */
731 ret = stringify_state(buf, buf_size, str, str_max);
732 if (ret)
733 return ret;
734
735 return 0;
736}
737
Simon Glass66262ed2020-02-06 09:55:04 -0700738static int cr50_i2c_open(struct udevice *dev)
739{
740 char buf[80];
741 int ret;
742
743 ret = process_reset(dev);
744 if (ret)
745 return log_msg_ret("reset", ret);
746
747 ret = claim_locality(dev, 0);
748 if (ret)
749 return log_msg_ret("claim", ret);
750
751 cr50_i2c_get_desc(dev, buf, sizeof(buf));
752 log_debug("%s\n", buf);
753
754 return 0;
755}
756
757static int cr50_i2c_cleanup(struct udevice *dev)
758{
Simon Glassfec444c2020-04-08 16:57:22 -0600759 struct cr50_priv *priv = dev_get_priv(dev);
760
Simon Glass5726f2f2020-09-27 18:46:24 -0600761 log_debug("cleanup %d\n", priv->locality);
Simon Glassfec444c2020-04-08 16:57:22 -0600762 if (priv->locality != -1)
763 release_locality(dev, 1);
Simon Glass66262ed2020-02-06 09:55:04 -0700764
765 return 0;
766}
767
Simon Glass11b1a272020-09-22 12:45:24 -0600768static int cr50_acpi_fill_ssdt(const struct udevice *dev, struct acpi_ctx *ctx)
769{
770 char scope[ACPI_PATH_MAX];
771 char name[ACPI_NAME_MAX];
772 const char *hid;
773 int ret;
774
775 ret = acpi_device_scope(dev, scope, sizeof(scope));
776 if (ret)
777 return log_msg_ret("scope", ret);
778 ret = acpi_get_name(dev, name);
779 if (ret)
780 return log_msg_ret("name", ret);
781
782 hid = dev_read_string(dev, "acpi,hid");
783 if (!hid)
784 return log_msg_ret("hid", ret);
785
786 /* Device */
787 acpigen_write_scope(ctx, scope);
788 acpigen_write_device(ctx, name);
789 acpigen_write_name_string(ctx, "_HID", hid);
790 acpigen_write_name_integer(ctx, "_UID",
791 dev_read_u32_default(dev, "acpi,uid", 0));
792 acpigen_write_name_string(ctx, "_DDN",
793 dev_read_string(dev, "acpi,ddn"));
794 acpigen_write_sta(ctx, acpi_device_status(dev));
795
796 /* Resources */
797 acpigen_write_name(ctx, "_CRS");
798 acpigen_write_resourcetemplate_header(ctx);
799 ret = acpi_device_write_i2c_dev(ctx, dev);
800 if (ret < 0)
801 return log_msg_ret("i2c", ret);
802 ret = acpi_device_write_interrupt_or_gpio(ctx, (struct udevice *)dev,
803 "ready-gpios");
804 if (ret < 0)
805 return log_msg_ret("irq_gpio", ret);
806
807 acpigen_write_resourcetemplate_footer(ctx);
808
809 acpigen_pop_len(ctx); /* Device */
810 acpigen_pop_len(ctx); /* Scope */
811
812 return 0;
813}
814
Simon Glass66262ed2020-02-06 09:55:04 -0700815enum {
816 TPM_TIMEOUT_MS = 5,
817 SHORT_TIMEOUT_MS = 750,
818 LONG_TIMEOUT_MS = 2000,
819};
820
Simon Glassaad29ae2020-12-03 16:55:21 -0700821static int cr50_i2c_of_to_plat(struct udevice *dev)
Simon Glass66262ed2020-02-06 09:55:04 -0700822{
823 struct tpm_chip_priv *upriv = dev_get_uclass_priv(dev);
824 struct cr50_priv *priv = dev_get_priv(dev);
825 struct irq irq;
826 int ret;
827
828 upriv->version = TPM_V2;
829 upriv->duration_ms[TPM_SHORT] = SHORT_TIMEOUT_MS;
830 upriv->duration_ms[TPM_MEDIUM] = LONG_TIMEOUT_MS;
831 upriv->duration_ms[TPM_LONG] = LONG_TIMEOUT_MS;
832 upriv->retry_time_ms = TPM_TIMEOUT_MS;
833
834 upriv->pcr_count = 32;
835 upriv->pcr_select_min = 2;
836
837 /* Optional GPIO to track when cr50 is ready */
838 ret = irq_get_by_index(dev, 0, &irq);
839 if (!ret) {
840 priv->irq = irq;
841 priv->use_irq = true;
842 } else {
Simon Glass3c42e422020-04-08 16:57:24 -0600843 ret = gpio_request_by_name(dev, "ready-gpios", 0,
Simon Glass66262ed2020-02-06 09:55:04 -0700844 &priv->ready_gpio, GPIOD_IS_IN);
845 if (ret) {
846 log_warning("Cr50 does not have an ready GPIO/interrupt (err=%d)\n",
847 ret);
848 }
849 }
850
851 return 0;
852}
853
854static int cr50_i2c_probe(struct udevice *dev)
855{
856 struct cr50_priv *priv = dev_get_priv(dev);
857 u32 vendor = 0;
858 ulong start;
859
860 /*
861 * 150ms should be enough to synchronise with the TPM even under the
862 * worst nested-reset-request conditions. In the vast majority of cases
863 * there will be no wait at all.
864 */
865 start = get_timer(0);
866 while (get_timer(start) < 150) {
867 int ret;
868
869 /* Exit once DID and VID verified */
870 ret = cr50_i2c_read(dev, tpm_did_vid(0), (u8 *)&vendor, 4);
871 if (!ret && vendor == CR50_DID_VID)
872 break;
873
874 /* TPM might be resetting; let's retry in a bit */
875 mdelay(10);
876 }
877 if (vendor != CR50_DID_VID) {
Simon Glass8e5f3452020-12-31 09:52:13 -0700878 log_warning("DID_VID %08x not recognised\n", vendor);
Simon Glass66262ed2020-02-06 09:55:04 -0700879 return log_msg_ret("vendor-id", -EXDEV);
880 }
881 priv->vendor = vendor;
Simon Glassfec444c2020-04-08 16:57:22 -0600882 priv->locality = -1;
Simon Glass8e5f3452020-12-31 09:52:13 -0700883 log_debug("Cr50 ready\n");
Simon Glass66262ed2020-02-06 09:55:04 -0700884
885 return 0;
886}
887
Simon Glass11b1a272020-09-22 12:45:24 -0600888struct acpi_ops cr50_acpi_ops = {
889 .fill_ssdt = cr50_acpi_fill_ssdt,
890};
891
Simon Glass66262ed2020-02-06 09:55:04 -0700892static const struct tpm_ops cr50_i2c_ops = {
893 .open = cr50_i2c_open,
894 .get_desc = cr50_i2c_get_desc,
Simon Glass3f7a73a2022-08-30 21:05:37 -0600895 .report_state = cr50_i2c_report_state,
Simon Glass66262ed2020-02-06 09:55:04 -0700896 .send = cr50_i2c_send,
897 .recv = cr50_i2c_recv,
898 .cleanup = cr50_i2c_cleanup,
899};
900
901static const struct udevice_id cr50_i2c_ids[] = {
902 { .compatible = "google,cr50" },
903 { }
904};
905
Simon Glass21c6e8e2020-12-31 09:52:14 -0700906U_BOOT_DRIVER(google_cr50) = {
907 .name = "google_cr50",
Simon Glass66262ed2020-02-06 09:55:04 -0700908 .id = UCLASS_TPM,
909 .of_match = cr50_i2c_ids,
910 .ops = &cr50_i2c_ops,
Simon Glassaad29ae2020-12-03 16:55:21 -0700911 .of_to_plat = cr50_i2c_of_to_plat,
Simon Glass66262ed2020-02-06 09:55:04 -0700912 .probe = cr50_i2c_probe,
Simon Glassfec444c2020-04-08 16:57:22 -0600913 .remove = cr50_i2c_cleanup,
Simon Glass8a2b47f2020-12-03 16:55:17 -0700914 .priv_auto = sizeof(struct cr50_priv),
Simon Glass11b1a272020-09-22 12:45:24 -0600915 ACPI_OPS_PTR(&cr50_acpi_ops)
Simon Glassfec444c2020-04-08 16:57:22 -0600916 .flags = DM_FLAG_OS_PREPARE,
Simon Glass66262ed2020-02-06 09:55:04 -0700917};