Commit 5af7f115 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull tpm updates from James Morris:

 - Clean up the transmission flow

   Cleaned up the whole transmission flow. Locking of the chip is now
   done in the level of tpm_try_get_ops() and tpm_put_ops() instead
   taking the chip lock inside tpm_transmit(). The nested calls inside
   tpm_transmit(), used with the resource manager, have been refactored
   out.

   Should make easier to perform more complex transactions with the TPM
   without making the subsystem a bigger mess (e.g. encrypted channel
   patches by James Bottomley).

 - PPI 1.3 support

   TPM PPI 1.3 introduces an additional optional command parameter that
   may be needed for some commands. Display the parameter if the command
   requires such a parameter. Only command 23 (SetPCRBanks) needs one.

   The PPI request file will show output like this then:

      # echo "23 16" > request
      # cat request
      23 16

      # echo "5" > request
      # cat request
      5

 - Extend all PCR banks in IMA

   Instead of static PCR banks array, the array of available PCR banks
   is now allocated dynamically. The digests sizes are determined
   dynamically using a probe PCR read without relying crypto's static
   list of hash algorithms.

   This should finally make sealing of measurements in IMA safe and
   secure.

 - TPM 2.0 selftests

   Added a test suite to tools/testing/selftests/tpm2 previously outside
   of the kernel tree: https://github.com/jsakkine-intel/tpm2-scripts

* 'next-tpm' of git://git.kernel.org/pub/scm/linux/kernel/git/jmorris/linux-security: (37 commits)
  tpm/ppi: Enable submission of optional command parameter for PPI 1.3
  tpm/ppi: Possibly show command parameter if TPM PPI 1.3 is used
  tpm/ppi: Display up to 101 operations as define for version 1.3
  tpm/ppi: rename TPM_PPI_REVISION_ID to TPM_PPI_REVISION_ID_1
  tpm/ppi: pass function revision ID to tpm_eval_dsm()
  tpm: pass an array of tpm_extend_digest structures to tpm_pcr_extend()
  KEYS: trusted: explicitly use tpm_chip structure from tpm_default_chip()
  tpm: move tpm_chip definition to include/linux/tpm.h
  tpm: retrieve digest size of unknown algorithms with PCR read
  tpm: rename and export tpm2_digest and tpm2_algorithms
  tpm: dynamically allocate the allocated_banks array
  tpm: remove @flags from tpm_transmit()
  tpm: take TPM chip power gating out of tpm_transmit()
  tpm: introduce tpm_chip_start() and tpm_chip_stop()
  tpm: remove TPM_TRANSMIT_UNLOCKED flag
  tpm: use tpm_try_get_ops() in tpm-sysfs.c.
  tpm: remove @space from tpm_transmit()
  tpm: move TPM space code out of tpm_transmit()
  tpm: move tpm_validate_commmand() to tpm2-space.c
  tpm: clean up tpm_try_transmit() error handling flow
  ...
parents c3665a6b 5da10728
Loading
Loading
Loading
Loading
+16 −25
Original line number Diff line number Diff line
@@ -74,7 +74,7 @@ static const char* tcpa_pc_event_id_strings[] = {
/* returns pointer to start of pos. entry of tcg log */
static void *tpm1_bios_measurements_start(struct seq_file *m, loff_t *pos)
{
	loff_t i;
	loff_t i = 0;
	struct tpm_chip *chip = m->private;
	struct tpm_bios_log *log = &chip->log;
	void *addr = log->bios_event_log;
@@ -83,39 +83,30 @@ static void *tpm1_bios_measurements_start(struct seq_file *m, loff_t *pos)
	u32 converted_event_size;
	u32 converted_event_type;


	/* read over *pos measurements */
	for (i = 0; i < *pos; i++) {
	do {
		event = addr;

		/* check if current entry is valid */
		if (addr + sizeof(struct tcpa_event) > limit)
			return NULL;

		converted_event_size =
		    do_endian_conversion(event->event_size);
		converted_event_type =
		    do_endian_conversion(event->event_type);

		if ((addr + sizeof(struct tcpa_event)) < limit) {
			if ((converted_event_type == 0) &&
			    (converted_event_size == 0))
				return NULL;
			addr += (sizeof(struct tcpa_event) +
				 converted_event_size);
		}
	}

	/* now check if current entry is valid */
	if ((addr + sizeof(struct tcpa_event)) >= limit)
		return NULL;

	event = addr;

	converted_event_size = do_endian_conversion(event->event_size);
	converted_event_type = do_endian_conversion(event->event_type);

		if (((converted_event_type == 0) && (converted_event_size == 0))
		    || ((addr + sizeof(struct tcpa_event) + converted_event_size)
		>= limit))
			> limit))
			return NULL;

		if (i++ == *pos)
			break;

		addr += (sizeof(struct tcpa_event) + converted_event_size);
	} while (1);

	return addr;
}

@@ -134,7 +125,7 @@ static void *tpm1_bios_measurements_next(struct seq_file *m, void *v,
	v += sizeof(struct tcpa_event) + converted_event_size;

	/* now check if current entry is valid */
	if ((v + sizeof(struct tcpa_event)) >= limit)
	if ((v + sizeof(struct tcpa_event)) > limit)
		return NULL;

	event = v;
@@ -143,7 +134,7 @@ static void *tpm1_bios_measurements_next(struct seq_file *m, void *v,
	converted_event_type = do_endian_conversion(event->event_type);

	if (((converted_event_type == 0) && (converted_event_size == 0)) ||
	    ((v + sizeof(struct tcpa_event) + converted_event_size) >= limit))
	    ((v + sizeof(struct tcpa_event) + converted_event_size) > limit))
		return NULL;

	(*pos)++;
+6 −6
Original line number Diff line number Diff line
@@ -37,10 +37,10 @@
 *
 * Returns size of the event. If it is an invalid event, returns 0.
 */
static int calc_tpm2_event_size(struct tcg_pcr_event2 *event,
static int calc_tpm2_event_size(struct tcg_pcr_event2_head *event,
				struct tcg_pcr_event *event_header)
{
	struct tcg_efi_specid_event *efispecid;
	struct tcg_efi_specid_event_head *efispecid;
	struct tcg_event_field *event_field;
	void *marker;
	void *marker_start;
@@ -55,7 +55,7 @@ static int calc_tpm2_event_size(struct tcg_pcr_event2 *event,
	marker = marker + sizeof(event->pcr_idx) + sizeof(event->event_type)
		+ sizeof(event->count);

	efispecid = (struct tcg_efi_specid_event *)event_header->event;
	efispecid = (struct tcg_efi_specid_event_head *)event_header->event;

	/* Check if event is malformed. */
	if (event->count > efispecid->num_algs)
@@ -95,7 +95,7 @@ static void *tpm2_bios_measurements_start(struct seq_file *m, loff_t *pos)
	void *addr = log->bios_event_log;
	void *limit = log->bios_event_log_end;
	struct tcg_pcr_event *event_header;
	struct tcg_pcr_event2 *event;
	struct tcg_pcr_event2_head *event;
	size_t size;
	int i;

@@ -136,7 +136,7 @@ static void *tpm2_bios_measurements_next(struct seq_file *m, void *v,
					 loff_t *pos)
{
	struct tcg_pcr_event *event_header;
	struct tcg_pcr_event2 *event;
	struct tcg_pcr_event2_head *event;
	struct tpm_chip *chip = m->private;
	struct tpm_bios_log *log = &chip->log;
	void *limit = log->bios_event_log_end;
@@ -180,7 +180,7 @@ static int tpm2_binary_bios_measurements_show(struct seq_file *m, void *v)
	struct tpm_chip *chip = m->private;
	struct tpm_bios_log *log = &chip->log;
	struct tcg_pcr_event *event_header = log->bios_event_log;
	struct tcg_pcr_event2 *event = v;
	struct tcg_pcr_event2_head *event = v;
	void *temp_ptr;
	size_t size;

+1 −1
Original line number Diff line number Diff line
@@ -33,7 +33,7 @@

struct st33zp24_i2c_phy {
	struct i2c_client *client;
	u8 buf[TPM_BUFSIZE + 1];
	u8 buf[ST33ZP24_BUFSIZE + 1];
	int io_lpcpd;
};

+1 −1
Original line number Diff line number Diff line
@@ -63,7 +63,7 @@
 * some latency byte before the answer is available (max 15).
 * We have 2048 + 1024 + 15.
 */
#define ST33ZP24_SPI_BUFFER_SIZE (TPM_BUFSIZE + (TPM_BUFSIZE / 2) +\
#define ST33ZP24_SPI_BUFFER_SIZE (ST33ZP24_BUFSIZE + (ST33ZP24_BUFSIZE / 2) +\
				  MAX_SPI_LATENCY)


+1 −1
Original line number Diff line number Diff line
@@ -436,7 +436,7 @@ static int st33zp24_send(struct tpm_chip *chip, unsigned char *buf,
			goto out_err;
	}

	return len;
	return 0;
out_err:
	st33zp24_cancel(chip);
	release_locality(chip);
Loading