All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 01/10] tpm: Check received number of bytes against length indicator in header
@ 2017-01-10 14:18 Stefan Berger
  2017-01-10 14:18 ` [PATCH 05/10] tpm: tpm2_seal_trusted: check size of response before accessing data Stefan Berger
                   ` (4 more replies)
  0 siblings, 5 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel; +Cc: linux-security-module, jarkko.sakkinen, Stefan Berger

Make sure that we have not received less bytes than what is indicated
in the header of the TPM response.

Signed-off-by: Stefan Berger <stefanb@linux.vnet.ibm.com>
---
 drivers/char/tpm/tpm-interface.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/char/tpm/tpm-interface.c b/drivers/char/tpm/tpm-interface.c
index fecdd3f..9d6f894 100644
--- a/drivers/char/tpm/tpm-interface.c
+++ b/drivers/char/tpm/tpm-interface.c
@@ -446,6 +446,8 @@ ssize_t tpm_transmit_cmd(struct tpm_chip *chip, const void *cmd,
 		return -EFAULT;
 
 	header = cmd;
+	if (len < be32_to_cpu(header->length))
+		return -EFAULT;
 
 	err = be32_to_cpu(header->return_code);
 	if (err != 0 && desc)
-- 
2.4.3


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 02/10] tpm: tpm2_get_tpm_pt: check size of response before accessing data
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
@ 2017-01-10 14:18   ` Stefan Berger
  2017-01-10 14:18   ` [PATCH 03/10] tpm: tpm2_pcr_read: " Stefan Berger
                     ` (5 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
---
 drivers/char/tpm/tpm2-cmd.c | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c
index 6eda239..d302f06 100644
--- a/drivers/char/tpm/tpm2-cmd.c
+++ b/drivers/char/tpm/tpm2-cmd.c
@@ -394,6 +394,10 @@ int tpm2_get_random(struct tpm_chip *chip, u8 *out, size_t max)
 	(sizeof(struct tpm_input_header) + \
 	 sizeof(struct tpm2_get_tpm_pt_in))
 
+#define TPM2_GET_TPM_PT_OUT_SIZE \
+	(sizeof(struct tpm_output_header) + \
+	 sizeof(struct tpm2_get_tpm_pt_out))
+
 static const struct tpm_input_header tpm2_get_tpm_pt_header = {
 	.tag = cpu_to_be16(TPM2_ST_NO_SESSIONS),
 	.length = cpu_to_be32(TPM2_GET_TPM_PT_IN_SIZE),
@@ -740,6 +744,8 @@ ssize_t tpm2_get_tpm_pt(struct tpm_chip *chip, u32 property_id,  u32 *value,
 	cmd.params.get_tpm_pt_in.property_cnt = cpu_to_be32(1);
 
 	rc = tpm_transmit_cmd(chip, &cmd, sizeof(cmd), 0, desc);
+	if (be32_to_cpu(cmd.header.out.length) < TPM2_GET_TPM_PT_OUT_SIZE)
+		return -EFAULT;
 	if (!rc)
 		*value = be32_to_cpu(cmd.params.get_tpm_pt_out.value);
 
-- 
2.4.3


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 03/10] tpm: tpm2_pcr_read: check size of response before accessing data
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
  2017-01-10 14:18   ` [PATCH 02/10] tpm: tpm2_get_tpm_pt: " Stefan Berger
@ 2017-01-10 14:18   ` Stefan Berger
  2017-01-10 16:18     ` [tpmdd-devel] " Jason Gunthorpe
  2017-01-10 14:18   ` [PATCH 04/10] tpm: tpm2_get_random: " Stefan Berger
                     ` (4 subsequent siblings)
  6 siblings, 1 reply; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
---
 drivers/char/tpm/tpm2-cmd.c | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c
index d302f06..e3f760c 100644
--- a/drivers/char/tpm/tpm2-cmd.c
+++ b/drivers/char/tpm/tpm2-cmd.c
@@ -248,6 +248,10 @@ static const u8 tpm2_ordinal_duration[TPM2_CC_LAST - TPM2_CC_FIRST + 1] = {
 	(sizeof(struct tpm_input_header) + \
 	 sizeof(struct tpm2_pcr_read_in))
 
+#define TPM2_PCR_READ_OUT_SIZE \
+	(sizeof(struct tpm_output_header) + \
+	 sizeof(struct tpm2_pcr_read_out))
+
 static const struct tpm_input_header tpm2_pcrread_header = {
 	.tag = cpu_to_be16(TPM2_ST_NO_SESSIONS),
 	.length = cpu_to_be32(TPM2_PCR_READ_IN_SIZE),
@@ -282,6 +286,9 @@ int tpm2_pcr_read(struct tpm_chip *chip, int pcr_idx, u8 *res_buf)
 
 	rc = tpm_transmit_cmd(chip, &cmd, sizeof(cmd), 0,
 			      "attempting to read a pcr value");
+	if (rc == 0 &&
+	    be32_to_cpu(cmd.header.out.length) < TPM2_PCR_READ_OUT_SIZE)
+		return -EFAULT;
 	if (rc == 0) {
 		buf = cmd.params.pcrread_out.digest;
 		memcpy(res_buf, buf, TPM_DIGEST_SIZE);
-- 
2.4.3


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 04/10] tpm: tpm2_get_random: check size of response before accessing data
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
  2017-01-10 14:18   ` [PATCH 02/10] tpm: tpm2_get_tpm_pt: " Stefan Berger
  2017-01-10 14:18   ` [PATCH 03/10] tpm: tpm2_pcr_read: " Stefan Berger
@ 2017-01-10 14:18   ` Stefan Berger
  2017-01-10 14:18   ` [PATCH 06/10] tpm: tpm2_load_cmd: " Stefan Berger
                     ` (3 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
---
 drivers/char/tpm/tpm2-cmd.c | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c
index e3f760c..1e704a1 100644
--- a/drivers/char/tpm/tpm2-cmd.c
+++ b/drivers/char/tpm/tpm2-cmd.c
@@ -363,7 +363,7 @@ static const struct tpm_input_header tpm2_getrandom_header = {
 int tpm2_get_random(struct tpm_chip *chip, u8 *out, size_t max)
 {
 	struct tpm2_cmd cmd;
-	u32 recd;
+	u32 recd, rlength;
 	u32 num_bytes;
 	int err;
 	int total = 0;
@@ -385,8 +385,16 @@ int tpm2_get_random(struct tpm_chip *chip, u8 *out, size_t max)
 		if (err)
 			break;
 
+		rlength = be32_to_cpu(cmd.header.out.length);
+		if (rlength < offsetof(struct tpm2_cmd,
+				       params.getrandom_out.buffer))
+			return -EFAULT;
+
 		recd = min_t(u32, be16_to_cpu(cmd.params.getrandom_out.size),
 			     num_bytes);
+		if (rlength < offsetof(struct tpm2_cmd,
+				       params.getrandom_out.buffer) + recd)
+			return -EFAULT;
 		memcpy(dest, cmd.params.getrandom_out.buffer, recd);
 
 		dest += recd;
-- 
2.4.3


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 05/10] tpm: tpm2_seal_trusted: check size of response before accessing data
  2017-01-10 14:18 [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Stefan Berger
@ 2017-01-10 14:18 ` Stefan Berger
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
                   ` (3 subsequent siblings)
  4 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel; +Cc: linux-security-module, jarkko.sakkinen, Stefan Berger

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb@linux.vnet.ibm.com>
---
 drivers/char/tpm/tpm2-cmd.c | 12 +++++++++++-
 1 file changed, 11 insertions(+), 1 deletion(-)

diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c
index 1e704a1..57bb774 100644
--- a/drivers/char/tpm/tpm2-cmd.c
+++ b/drivers/char/tpm/tpm2-cmd.c
@@ -464,7 +464,7 @@ int tpm2_seal_trusted(struct tpm_chip *chip,
 {
 	unsigned int blob_len;
 	struct tpm_buf buf;
-	u32 hash;
+	u32 hash, rlength;
 	int i;
 	int rc;
 
@@ -533,11 +533,21 @@ int tpm2_seal_trusted(struct tpm_chip *chip,
 	if (rc)
 		goto out;
 
+	rlength = be32_to_cpu(((struct tpm2_cmd*)&buf)->header.out.length);
+	if (rlength < TPM_HEADER_SIZE + 4) {
+		rc = -EFAULT;
+		goto out;
+	}
+
 	blob_len = be32_to_cpup((__be32 *) &buf.data[TPM_HEADER_SIZE]);
 	if (blob_len > MAX_BLOB_SIZE) {
 		rc = -E2BIG;
 		goto out;
 	}
+	if (rlength < TPM_HEADER_SIZE + 4 + blob_len) {
+		rc = -EFAULT;
+		goto out;
+	}
 
 	memcpy(payload->blob, &buf.data[TPM_HEADER_SIZE + 4], blob_len);
 	payload->blob_len = blob_len;
-- 
2.4.3


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 06/10] tpm: tpm2_load_cmd: check size of response before accessing data
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
                     ` (2 preceding siblings ...)
  2017-01-10 14:18   ` [PATCH 04/10] tpm: tpm2_get_random: " Stefan Berger
@ 2017-01-10 14:18   ` Stefan Berger
  2017-01-10 14:18   ` [PATCH 07/10] tpm: tpm2_unseal_cmd: " Stefan Berger
                     ` (2 subsequent siblings)
  6 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
---
 drivers/char/tpm/tpm2-cmd.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c
index 57bb774..4bcda2b 100644
--- a/drivers/char/tpm/tpm2-cmd.c
+++ b/drivers/char/tpm/tpm2-cmd.c
@@ -618,6 +618,9 @@ static int tpm2_load_cmd(struct tpm_chip *chip,
 	}
 
 	rc = tpm_transmit_cmd(chip, buf.data, PAGE_SIZE, flags, "loading blob");
+	if (!rc && be32_to_cpu(((struct tpm2_cmd *)&buf)->header.out.length) <
+                   TPM_HEADER_SIZE + 4)
+		rc = -EFAULT;
 	if (!rc)
 		*blob_handle = be32_to_cpup(
 			(__be32 *) &buf.data[TPM_HEADER_SIZE]);
-- 
2.4.3


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 07/10] tpm: tpm2_unseal_cmd: check size of response before accessing data
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
                     ` (3 preceding siblings ...)
  2017-01-10 14:18   ` [PATCH 06/10] tpm: tpm2_load_cmd: " Stefan Berger
@ 2017-01-10 14:18   ` Stefan Berger
  2017-01-10 14:18   ` [PATCH 08/10] tpm: tpm_getcap: " Stefan Berger
  2017-01-10 14:18   ` [PATCH 09/10] tpm: tpm_get_random: " Stefan Berger
  6 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
---
 drivers/char/tpm/tpm2-cmd.c | 13 +++++++++++++
 1 file changed, 13 insertions(+)

diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c
index 4bcda2b..f55e876 100644
--- a/drivers/char/tpm/tpm2-cmd.c
+++ b/drivers/char/tpm/tpm2-cmd.c
@@ -689,6 +689,7 @@ static int tpm2_unseal_cmd(struct tpm_chip *chip,
 	u16 data_len;
 	u8 *data;
 	int rc;
+	u32 rlength;
 
 	rc = tpm_buf_init(&buf, TPM2_ST_SESSIONS, TPM2_CC_UNSEAL);
 	if (rc)
@@ -708,8 +709,19 @@ static int tpm2_unseal_cmd(struct tpm_chip *chip,
 		rc = -EPERM;
 
 	if (!rc) {
+		rlength = be32_to_cpu(((struct tpm2_cmd *)&buf)
+					->header.out.length);
+		if (rlength < TPM_HEADER_SIZE + 4 + 2) {
+			rc = -EFAULT;
+			goto out;
+		}
 		data_len = be16_to_cpup(
 			(__be16 *) &buf.data[TPM_HEADER_SIZE + 4]);
+
+		if (rlength < TPM_HEADER_SIZE + 4 + 2 + data_len) {
+			rc = -EFAULT;
+			goto out;
+		}
 		data = &buf.data[TPM_HEADER_SIZE + 6];
 
 		memcpy(payload->key, data, data_len - 1);
@@ -717,6 +729,7 @@ static int tpm2_unseal_cmd(struct tpm_chip *chip,
 		payload->migratable = data[data_len - 1];
 	}
 
+out:
 	tpm_buf_destroy(&buf);
 	return rc;
 }
-- 
2.4.3


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 08/10] tpm: tpm_getcap: check size of response before accessing data
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
                     ` (4 preceding siblings ...)
  2017-01-10 14:18   ` [PATCH 07/10] tpm: tpm2_unseal_cmd: " Stefan Berger
@ 2017-01-10 14:18   ` Stefan Berger
  2017-01-10 14:18   ` [PATCH 09/10] tpm: tpm_get_random: " Stefan Berger
  6 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
---
 drivers/char/tpm/tpm-interface.c | 14 ++++++++++----
 drivers/char/tpm/tpm-sysfs.c     | 24 ++++++++++++++++--------
 drivers/char/tpm/tpm.h           |  2 +-
 drivers/char/tpm/tpm_tis_core.c  |  3 ++-
 4 files changed, 29 insertions(+), 14 deletions(-)

diff --git a/drivers/char/tpm/tpm-interface.c b/drivers/char/tpm/tpm-interface.c
index 9d6f894..f80df9c 100644
--- a/drivers/char/tpm/tpm-interface.c
+++ b/drivers/char/tpm/tpm-interface.c
@@ -470,7 +470,7 @@ static const struct tpm_input_header tpm_getcap_header = {
 };
 
 ssize_t tpm_getcap(struct tpm_chip *chip, u32 subcap_id, cap_t *cap,
-		   const char *desc)
+		   const char *desc, size_t exp_rlength)
 {
 	struct tpm_cmd_t tpm_cmd;
 	int rc;
@@ -495,6 +495,9 @@ ssize_t tpm_getcap(struct tpm_chip *chip, u32 subcap_id, cap_t *cap,
 	}
 	rc = tpm_transmit_cmd(chip, &tpm_cmd, TPM_INTERNAL_RESULT_SIZE, 0,
 			      desc);
+	if (!rc && be32_to_cpu(tpm_cmd.header.out.length) < exp_rlength)
+		return -EFAULT;
+
 	if (!rc)
 		*cap = tpm_cmd.params.getcap_out.cap;
 	return rc;
@@ -548,7 +551,8 @@ int tpm_get_timeouts(struct tpm_chip *chip)
 		return 0;
 	}
 
-	rc = tpm_getcap(chip, TPM_CAP_PROP_TIS_TIMEOUT, &cap, NULL);
+	rc = tpm_getcap(chip, TPM_CAP_PROP_TIS_TIMEOUT, &cap, NULL,
+	                TPM_HEADER_SIZE + sizeof(cap.timeout));
 	if (rc == TPM_ERR_INVALID_POSTINIT) {
 		/* The TPM is not started, we are the first to talk to it.
 		   Execute a startup command. */
@@ -557,7 +561,8 @@ int tpm_get_timeouts(struct tpm_chip *chip)
 			return rc;
 
 		rc = tpm_getcap(chip, TPM_CAP_PROP_TIS_TIMEOUT, &cap,
-				"attempting to determine the timeouts");
+				"attempting to determine the timeouts",
+				TPM_HEADER_SIZE + sizeof(cap.timeout));
 	}
 	if (rc) {
 		dev_err(&chip->dev,
@@ -608,7 +613,8 @@ int tpm_get_timeouts(struct tpm_chip *chip)
 	chip->timeout_d = usecs_to_jiffies(new_timeout[3]);
 
 	rc = tpm_getcap(chip, TPM_CAP_PROP_TIS_DURATION, &cap,
-			"attempting to determine the durations");
+			"attempting to determine the durations",
+			TPM_HEAER_SIZE + sizeof(cap.duration));
 	if (rc)
 		return rc;
 
diff --git a/drivers/char/tpm/tpm-sysfs.c b/drivers/char/tpm/tpm-sysfs.c
index 848ad65..73d110d 100644
--- a/drivers/char/tpm/tpm-sysfs.c
+++ b/drivers/char/tpm/tpm-sysfs.c
@@ -95,7 +95,8 @@ static ssize_t pcrs_show(struct device *dev, struct device_attribute *attr,
 	struct tpm_chip *chip = to_tpm_chip(dev);
 
 	rc = tpm_getcap(chip, TPM_CAP_PROP_PCR, &cap,
-			"attempting to determine the number of PCRS");
+			"attempting to determine the number of PCRS",
+			TPM_HEADER_SIZE + sizeof(cap.num_pcrs));
 	if (rc)
 		return 0;
 
@@ -120,7 +121,8 @@ static ssize_t enabled_show(struct device *dev, struct device_attribute *attr,
 	ssize_t rc;
 
 	rc = tpm_getcap(to_tpm_chip(dev), TPM_CAP_FLAG_PERM, &cap,
-			"attempting to determine the permanent enabled state");
+			"attempting to determine the permanent enabled state",
+			TPM_HEADER_SIZE + sizeof(cap.perm_flags));
 	if (rc)
 		return 0;
 
@@ -136,7 +138,8 @@ static ssize_t active_show(struct device *dev, struct device_attribute *attr,
 	ssize_t rc;
 
 	rc = tpm_getcap(to_tpm_chip(dev), TPM_CAP_FLAG_PERM, &cap,
-			"attempting to determine the permanent active state");
+			"attempting to determine the permanent active state",
+			TPM_HEADER_SIZE + sizeof(cap.perm_flags));
 	if (rc)
 		return 0;
 
@@ -152,7 +155,8 @@ static ssize_t owned_show(struct device *dev, struct device_attribute *attr,
 	ssize_t rc;
 
 	rc = tpm_getcap(to_tpm_chip(dev), TPM_CAP_PROP_OWNER, &cap,
-			"attempting to determine the owner state");
+			"attempting to determine the owner state",
+			TPM_HEADER_SIZE + sizeof(cap.owned));
 	if (rc)
 		return 0;
 
@@ -168,7 +172,8 @@ static ssize_t temp_deactivated_show(struct device *dev,
 	ssize_t rc;
 
 	rc = tpm_getcap(to_tpm_chip(dev), TPM_CAP_FLAG_VOL, &cap,
-			"attempting to determine the temporary state");
+			"attempting to determine the temporary state",
+			TPM_HEADER_SIZE + sizeof(cap.stclear_flags));
 	if (rc)
 		return 0;
 
@@ -186,7 +191,8 @@ static ssize_t caps_show(struct device *dev, struct device_attribute *attr,
 	char *str = buf;
 
 	rc = tpm_getcap(chip, TPM_CAP_PROP_MANUFACTURER, &cap,
-			"attempting to determine the manufacturer");
+			"attempting to determine the manufacturer",
+			TPM_HEADER_SIZE + sizeof(cap.manufacturer_id));
 	if (rc)
 		return 0;
 	str += sprintf(str, "Manufacturer: 0x%x\n",
@@ -194,7 +200,8 @@ static ssize_t caps_show(struct device *dev, struct device_attribute *attr,
 
 	/* Try to get a TPM version 1.2 TPM_CAP_VERSION_INFO */
 	rc = tpm_getcap(chip, TPM_CAP_VERSION_1_2, &cap,
-			"attempting to determine the 1.2 version");
+			"attempting to determine the 1.2 version",
+			TPM_HEADER_SIZE + sizeof(cap.tpm_version_1_2));
 	if (!rc) {
 		str += sprintf(str,
 			       "TCG version: %d.%d\nFirmware version: %d.%d\n",
@@ -205,7 +212,8 @@ static ssize_t caps_show(struct device *dev, struct device_attribute *attr,
 	} else {
 		/* Otherwise just use TPM_STRUCT_VER */
 		rc = tpm_getcap(chip, TPM_CAP_VERSION_1_1, &cap,
-				"attempting to determine the 1.1 version");
+				"attempting to determine the 1.1 version",
+				TPM_HEADER_SIZE + sizeof(cap.tpm_version));
 		if (rc)
 			return 0;
 		str += sprintf(str,
diff --git a/drivers/char/tpm/tpm.h b/drivers/char/tpm/tpm.h
index 1ae9768..8d223bb 100644
--- a/drivers/char/tpm/tpm.h
+++ b/drivers/char/tpm/tpm.h
@@ -496,7 +496,7 @@ ssize_t tpm_transmit(struct tpm_chip *chip, const u8 *buf, size_t bufsiz,
 ssize_t tpm_transmit_cmd(struct tpm_chip *chip, const void *cmd, int len,
 			 unsigned int flags, const char *desc);
 ssize_t tpm_getcap(struct tpm_chip *chip, u32 subcap_id, cap_t *cap,
-		   const char *desc);
+		   const char *desc, size_t exp_rlength);
 int tpm_get_timeouts(struct tpm_chip *);
 int tpm1_auto_startup(struct tpm_chip *chip);
 int tpm_do_selftest(struct tpm_chip *chip);
diff --git a/drivers/char/tpm/tpm_tis_core.c b/drivers/char/tpm/tpm_tis_core.c
index 7993678..5ce2316 100644
--- a/drivers/char/tpm/tpm_tis_core.c
+++ b/drivers/char/tpm/tpm_tis_core.c
@@ -552,7 +552,8 @@ static int tpm_tis_gen_interrupt(struct tpm_chip *chip)
 	if (chip->flags & TPM_CHIP_FLAG_TPM2)
 		return tpm2_get_tpm_pt(chip, 0x100, &cap2, desc);
 	else
-		return tpm_getcap(chip, TPM_CAP_PROP_TIS_TIMEOUT, &cap, desc);
+		return tpm_getcap(chip, TPM_CAP_PROP_TIS_TIMEOUT, &cap, desc,
+		                  TPM_HEADER_SIZE + sizeof(cap.timeout));
 }
 
 /* Register the IRQ and issue a command that will cause an interrupt. If an
-- 
2.4.3


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 09/10] tpm: tpm_get_random: check size of response before accessing data
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
                     ` (5 preceding siblings ...)
  2017-01-10 14:18   ` [PATCH 08/10] tpm: tpm_getcap: " Stefan Berger
@ 2017-01-10 14:18   ` Stefan Berger
  6 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
---
 drivers/char/tpm/tpm-interface.c | 14 ++++++++++++--
 1 file changed, 12 insertions(+), 2 deletions(-)

diff --git a/drivers/char/tpm/tpm-interface.c b/drivers/char/tpm/tpm-interface.c
index f80df9c..1c04a2d 100644
--- a/drivers/char/tpm/tpm-interface.c
+++ b/drivers/char/tpm/tpm-interface.c
@@ -1059,7 +1059,7 @@ int tpm_get_random(u32 chip_num, u8 *out, size_t max)
 {
 	struct tpm_chip *chip;
 	struct tpm_cmd_t tpm_cmd;
-	u32 recd, num_bytes = min_t(u32, max, TPM_MAX_RNG_DATA);
+	u32 recd, num_bytes = min_t(u32, max, TPM_MAX_RNG_DATA), rlength;
 	int err, total = 0, retries = 5;
 	u8 *dest = out;
 
@@ -1085,8 +1085,18 @@ int tpm_get_random(u32 chip_num, u8 *out, size_t max)
 				       0, "attempting get random");
 		if (err)
 			break;
-
+		rlength = be32_to_cpu(tpm_cmd.header.out.length);
+		if (rlength < offsetof(struct tpm_cmd_t,
+				       params.getrandom_out.rng_data)) {
+			total = -EFAULT;
+			break;
+		}
 		recd = be32_to_cpu(tpm_cmd.params.getrandom_out.rng_data_len);
+		if (rlength < offsetof(struct tpm_cmd_t,
+				       params.getrandom_out.rng_data) + recd) {
+			total = -EFAULT;
+			break;
+		}
 		memcpy(dest, tpm_cmd.params.getrandom_out.rng_data, recd);
 
 		dest += recd;
-- 
2.4.3


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 10/10] tpm: tpm_pcr_read_dev: check size of response before accessing data
  2017-01-10 14:18 [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Stefan Berger
  2017-01-10 14:18 ` [PATCH 05/10] tpm: tpm2_seal_trusted: check size of response before accessing data Stefan Berger
       [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
@ 2017-01-10 14:18 ` Stefan Berger
  2017-01-10 16:15 ` [tpmdd-devel] [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Jason Gunthorpe
  2017-01-12 14:45 ` Jarkko Sakkinen
  4 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 14:18 UTC (permalink / raw)
  To: tpmdd-devel; +Cc: linux-security-module, jarkko.sakkinen, Stefan Berger

Check the size of the response before accessing data in the
response packet. This is to avoid accessing data beyond the
end of the response.

Signed-off-by: Stefan Berger <stefanb@linux.vnet.ibm.com>
---
 drivers/char/tpm/tpm-interface.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/drivers/char/tpm/tpm-interface.c b/drivers/char/tpm/tpm-interface.c
index 1c04a2d..6b6f099 100644
--- a/drivers/char/tpm/tpm-interface.c
+++ b/drivers/char/tpm/tpm-interface.c
@@ -687,7 +687,9 @@ int tpm_pcr_read_dev(struct tpm_chip *chip, int pcr_idx, u8 *res_buf)
 	cmd.params.pcrread_in.pcr_idx = cpu_to_be32(pcr_idx);
 	rc = tpm_transmit_cmd(chip, &cmd, READ_PCR_RESULT_SIZE, 0,
 			      "attempting to read a pcr value");
-
+	if (rc == 0 &&
+	    be32_to_cpu(cmd.header.out.length) < READ_PCR_RESULT_SIZE)
+		return -EFAULT;
 	if (rc == 0)
 		memcpy(res_buf, cmd.params.pcrread_out.pcr_result,
 		       TPM_DIGEST_SIZE);
-- 
2.4.3


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* Re: [tpmdd-devel] [PATCH 01/10] tpm: Check received number of bytes against length indicator in header
  2017-01-10 14:18 [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Stefan Berger
                   ` (2 preceding siblings ...)
  2017-01-10 14:18 ` [PATCH 10/10] tpm: tpm_pcr_read_dev: " Stefan Berger
@ 2017-01-10 16:15 ` Jason Gunthorpe
       [not found]   ` <20170110161519.GC15493-ePGOBjL8dl3ta4EC/59zMFaTQe2KTcn/@public.gmane.org>
  2017-01-12 14:45 ` Jarkko Sakkinen
  4 siblings, 1 reply; 14+ messages in thread
From: Jason Gunthorpe @ 2017-01-10 16:15 UTC (permalink / raw)
  To: Stefan Berger; +Cc: tpmdd-devel, linux-security-module

On Tue, Jan 10, 2017 at 09:18:11AM -0500, Stefan Berger wrote:
> Make sure that we have not received less bytes than what is indicated
> in the header of the TPM response.

IMHO this entire series should be tagged for stable, can you please
add a Cc: and Fixes:

Thanks,
Jason

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [tpmdd-devel] [PATCH 03/10] tpm: tpm2_pcr_read: check size of response before accessing data
  2017-01-10 14:18   ` [PATCH 03/10] tpm: tpm2_pcr_read: " Stefan Berger
@ 2017-01-10 16:18     ` Jason Gunthorpe
  0 siblings, 0 replies; 14+ messages in thread
From: Jason Gunthorpe @ 2017-01-10 16:18 UTC (permalink / raw)
  To: Stefan Berger; +Cc: tpmdd-devel, linux-security-module

On Tue, Jan 10, 2017 at 09:18:13AM -0500, Stefan Berger wrote:
> Check the size of the response before accessing data in the
> response packet. This is to avoid accessing data beyond the
> end of the response.

IMHO you should chnage the signature for
tpm_transmit_cmd to be:

ssize_t tpm_transmit_cmd(struct tpm_chip *chip,
  void *iobuf, size_t tx_len,
  size_t min_rx_len,
  unsigned int flags,
  const char *desc);

And then fold this repeated:

>  	rc = tpm_transmit_cmd(chip, &cmd, sizeof(cmd), 0,
>  			      "attempting to read a pcr value");
> +	if (rc == 0 &&
> +	    be32_to_cpu(cmd.header.out.length) < TPM2_PCR_READ_OUT_SIZE)
> +		return -EFAULT;

test into tpm_transmit_cmd and now we require every single caller to
specify the minimum command length.

You can fold all of that into one patch, IMHO. Easier for stable.

Jason

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 01/10] tpm: Check received number of bytes against length indicator in header
       [not found]   ` <20170110161519.GC15493-ePGOBjL8dl3ta4EC/59zMFaTQe2KTcn/@public.gmane.org>
@ 2017-01-10 19:59     ` Stefan Berger
  0 siblings, 0 replies; 14+ messages in thread
From: Stefan Berger @ 2017-01-10 19:59 UTC (permalink / raw)
  To: Jason Gunthorpe
  Cc: linux-security-module-u79uwXL29TY76Z2rM5mHXA,
	tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f

On 01/10/2017 11:15 AM, Jason Gunthorpe wrote:
> On Tue, Jan 10, 2017 at 09:18:11AM -0500, Stefan Berger wrote:
>> Make sure that we have not received less bytes than what is indicated
>> in the header of the TPM response.
> IMHO this entire series should be tagged for stable, can you please
> add a Cc: and Fixes:

I don't have a way to test all the commands to make sure whether one is 
now failing. Several ones for TPM 1.2 are reachable via sysfs, but not 
so easy for TPM2. So I would suggest to try it out first, then propagate 
it into stable after some time.

     Stefan

>
> Thanks,
> Jason
>


------------------------------------------------------------------------------
Developer Access Program for Intel Xeon Phi Processors
Access to Intel Xeon Phi processor-based developer platforms.
With one year of Intel Parallel Studio XE.
Training and support from Colfax.
Order your platform today. http://sdm.link/xeonphi

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 01/10] tpm: Check received number of bytes against length indicator in header
  2017-01-10 14:18 [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Stefan Berger
                   ` (3 preceding siblings ...)
  2017-01-10 16:15 ` [tpmdd-devel] [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Jason Gunthorpe
@ 2017-01-12 14:45 ` Jarkko Sakkinen
  4 siblings, 0 replies; 14+ messages in thread
From: Jarkko Sakkinen @ 2017-01-12 14:45 UTC (permalink / raw)
  To: Stefan Berger; +Cc: tpmdd-devel, linux-security-module

On Tue, Jan 10, 2017 at 09:18:11AM -0500, Stefan Berger wrote:
> Make sure that we have not received less bytes than what is indicated
> in the header of the TPM response.
> 
> Signed-off-by: Stefan Berger <stefanb@linux.vnet.ibm.com>

NAK for the whole patch set as it is missing the cover letter.

Also you should pick my validation patch to this patch set and do the
check inside the new function.

/Jarkko

> ---
>  drivers/char/tpm/tpm-interface.c | 2 ++
>  1 file changed, 2 insertions(+)
> 
> diff --git a/drivers/char/tpm/tpm-interface.c b/drivers/char/tpm/tpm-interface.c
> index fecdd3f..9d6f894 100644
> --- a/drivers/char/tpm/tpm-interface.c
> +++ b/drivers/char/tpm/tpm-interface.c
> @@ -446,6 +446,8 @@ ssize_t tpm_transmit_cmd(struct tpm_chip *chip, const void *cmd,
>  		return -EFAULT;
>  
>  	header = cmd;
> +	if (len < be32_to_cpu(header->length))
> +		return -EFAULT;
>  
>  	err = be32_to_cpu(header->return_code);
>  	if (err != 0 && desc)
> -- 
> 2.4.3
> 

^ permalink raw reply	[flat|nested] 14+ messages in thread

end of thread, other threads:[~2017-01-12 14:45 UTC | newest]

Thread overview: 14+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-01-10 14:18 [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Stefan Berger
2017-01-10 14:18 ` [PATCH 05/10] tpm: tpm2_seal_trusted: check size of response before accessing data Stefan Berger
     [not found] ` <1484057900-17871-1-git-send-email-stefanb-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
2017-01-10 14:18   ` [PATCH 02/10] tpm: tpm2_get_tpm_pt: " Stefan Berger
2017-01-10 14:18   ` [PATCH 03/10] tpm: tpm2_pcr_read: " Stefan Berger
2017-01-10 16:18     ` [tpmdd-devel] " Jason Gunthorpe
2017-01-10 14:18   ` [PATCH 04/10] tpm: tpm2_get_random: " Stefan Berger
2017-01-10 14:18   ` [PATCH 06/10] tpm: tpm2_load_cmd: " Stefan Berger
2017-01-10 14:18   ` [PATCH 07/10] tpm: tpm2_unseal_cmd: " Stefan Berger
2017-01-10 14:18   ` [PATCH 08/10] tpm: tpm_getcap: " Stefan Berger
2017-01-10 14:18   ` [PATCH 09/10] tpm: tpm_get_random: " Stefan Berger
2017-01-10 14:18 ` [PATCH 10/10] tpm: tpm_pcr_read_dev: " Stefan Berger
2017-01-10 16:15 ` [tpmdd-devel] [PATCH 01/10] tpm: Check received number of bytes against length indicator in header Jason Gunthorpe
     [not found]   ` <20170110161519.GC15493-ePGOBjL8dl3ta4EC/59zMFaTQe2KTcn/@public.gmane.org>
2017-01-10 19:59     ` Stefan Berger
2017-01-12 14:45 ` Jarkko Sakkinen

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.