All of lore.kernel.org
 help / color / mirror / Atom feed
From: Jarkko Sakkinen <jarkko.sakkinen-VuQAYsv1563Yd54FQh9/CA@public.gmane.org>
To: Alexander Steffen
	<Alexander.Steffen-d0qZbvYSIPpWk0Htik3J/w@public.gmane.org>
Cc: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f@public.gmane.org
Subject: Re: [PATCH 3/3] tpm2-cmd: React correctly to RC_TESTING from self tests
Date: Sun, 20 Aug 2017 21:31:47 +0300	[thread overview]
Message-ID: <20170820183147.h2zun4exzczcyl5a@linux.intel.com> (raw)
In-Reply-To: <20170818121532.5764-3-Alexander.Steffen-d0qZbvYSIPpWk0Htik3J/w@public.gmane.org>

On Fri, Aug 18, 2017 at 02:15:32PM +0200, Alexander Steffen wrote:
> The TPM can choose one of two ways to react to the TPM2_SelfTest command.
> It can either run all self tests synchronously and then return RC_SUCCESS
> once all tests were successful. Or it can choose to run the tests
> asynchronously and return RC_TESTING immediately while the self tests still
> execute in the background.
> 
> The previous implementation apparently was not aware of those possibilities
> and attributed RC_TESTING to some prototype chips instead. With this change
> the return code of TPM2_SelfTest is interpreted correctly, i.e. the self
> test result is polled if and only if RC_TESTING is received. Unfortunately,
> the polling cannot be done in the most straightforward way, so the solution
> is explained with a comment in the code.
> 
> Signed-off-by: Alexander Steffen <Alexander.Steffen-d0qZbvYSIPpWk0Htik3J/w@public.gmane.org>
> ---
>  drivers/char/tpm/tpm2-cmd.c | 68 ++++++++++++++++++---------------------------
>  1 file changed, 27 insertions(+), 41 deletions(-)
> 
> diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c
> index e3d4cc3..d09032f 100644
> --- a/drivers/char/tpm/tpm2-cmd.c
> +++ b/drivers/char/tpm/tpm2-cmd.c
> @@ -834,68 +834,54 @@ static const struct tpm_input_header tpm2_selftest_header = {
>  };
>  
>  /**
> - * tpm2_continue_selftest() - start a self test
> - *
> - * @chip: TPM chip to use
> - * @full: test all commands instead of testing only those that were not
> - *        previously tested.
> - *
> - * Return: Same as with tpm_transmit_cmd with exception of RC_TESTING.
> - */
> -static int tpm2_start_selftest(struct tpm_chip *chip, bool full)
> -{
> -	int rc;
> -	struct tpm2_cmd cmd;
> -
> -	cmd.header.in = tpm2_selftest_header;
> -	cmd.params.selftest_in.full_test = full;
> -
> -	rc = tpm_transmit_cmd(chip, NULL, &cmd, TPM2_SELF_TEST_IN_SIZE, 0, 0,
> -			      "continue selftest");
> -
> -	/* At least some prototype chips seem to give RC_TESTING error
> -	 * immediately. This is a workaround for that.
> -	 */
> -	if (rc == TPM2_RC_TESTING) {
> -		dev_warn(&chip->dev, "Got RC_TESTING, ignoring\n");
> -		rc = 0;
> -	}
> -
> -	return rc;
> -}
> -
> -/**
>   * tpm2_do_selftest() - ensure that all self tests have passed
>   *
>   * @chip: TPM chip to use
>   *
>   * Return: Same as with tpm_transmit_cmd.
>   *
> - * During the self test TPM2 commands return with the error code RC_TESTING.
> - * Waiting is done by issuing PCR read until it executes successfully.
> + * The TPM can either run all self tests synchronously and then return
> + * RC_SUCCESS once all tests were successful. Or it can choose to run the tests
> + * asynchronously and return RC_TESTING immediately while the self tests still
> + * execute in the background. This function handles both cases and waits until
> + * all tests have completed.
>   */
>  static int tpm2_do_selftest(struct tpm_chip *chip)
>  {
>  	int rc;
>  	unsigned int delay_msec = 20;
>  	long duration;
> +	struct tpm2_cmd cmd;
>  
>  	duration = jiffies_to_msecs(
>  		tpm2_calc_ordinal_duration(chip, TPM2_CC_SELF_TEST));
>  
> -	rc = tpm2_start_selftest(chip, false);
> -	if (rc)
> -		return rc;
> -
>  	while (duration > 0) {
> -		/* Attempt to read a PCR value */
> -		rc = tpm2_pcr_read(chip, 0, NULL);
> -		if (rc < 0)
> -			break;
> +		cmd.header.in = tpm2_selftest_header;
> +		cmd.params.selftest_in.full_test = 0;
> +
> +		rc = tpm_transmit_cmd(chip, NULL, &cmd, TPM2_SELF_TEST_IN_SIZE,
> +				      0, 0, "continue selftest");
>  
>  		if (rc != TPM2_RC_TESTING)
>  			break;
>  
> +		/* If RC_TESTING is received, ideally the code should now poll
> +		 * the selfTestDone bit in the STS register, as this avoids
> +		 * sending more commands, that might interrupt self tests
> +		 * executing in the background and thus prevent them from ever
> +		 * completing.
> +		 * Unfortunately, it cannot be guaranteed that this bit is
> +		 * correctly implemented for all devices, so the next best thing
> +		 * would be to use TPM2_GetTestResult to query the test result.
> +		 * But the response to that command can be very long, and the
> +		 * code currently lacks the capabilities for efficient
> +		 * unmarshalling, so it is difficult to execute this command.
> +		 * Therefore, we simply run the TPM2_SelfTest command in a loop,
> +		 * which should complete eventually, since we only request the
> +		 * execution of self tests that have not yet been done.
> +		 */

This should be part of the commit message, not part of the code.

/Jarkko

> +
>  		msleep(delay_msec);
>  		duration -= delay_msec;
>  
> -- 
> 2.7.4
> 

------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot

  parent reply	other threads:[~2017-08-20 18:31 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-08-18 12:15 [PATCH 1/3] tpm2-cmd: Trigger only missing self tests Alexander Steffen
     [not found] ` <20170818121532.5764-1-Alexander.Steffen-d0qZbvYSIPpWk0Htik3J/w@public.gmane.org>
2017-08-18 12:15   ` [PATCH 2/3] tpm2-cmd: Use dynamic delay to wait for self test result Alexander Steffen
     [not found]     ` <20170818121532.5764-2-Alexander.Steffen-d0qZbvYSIPpWk0Htik3J/w@public.gmane.org>
2017-08-20 18:26       ` Jarkko Sakkinen
     [not found]         ` <20170820182632.ik4d5nfm2ggashiy-VuQAYsv1563Yd54FQh9/CA@public.gmane.org>
2017-08-22 17:44           ` Jarkko Sakkinen
2017-08-18 12:15   ` [PATCH 3/3] tpm2-cmd: React correctly to RC_TESTING from self tests Alexander Steffen
     [not found]     ` <20170818121532.5764-3-Alexander.Steffen-d0qZbvYSIPpWk0Htik3J/w@public.gmane.org>
2017-08-20 18:31       ` Jarkko Sakkinen [this message]
2017-08-19 17:16   ` [PATCH 1/3] tpm2-cmd: Trigger only missing " Jarkko Sakkinen
2017-08-20 18:25   ` Jarkko Sakkinen

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20170820183147.h2zun4exzczcyl5a@linux.intel.com \
    --to=jarkko.sakkinen-vuqaysv1563yd54fqh9/ca@public.gmane.org \
    --cc=Alexander.Steffen-d0qZbvYSIPpWk0Htik3J/w@public.gmane.org \
    --cc=tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f@public.gmane.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.