security/tpm/tss/tcg-2.0: Add `tlcl_set_bits()`

This commit adds support for the TPM2_NV_SetBits command to the TLCL.
This command is used to set bits in an NV index that was created as a
bit field.  Any number of bits from 0 to 64 may be set.  The contents of
bits are ORed with the current contents of the NV index.

The following is an excerpt from lalala undergoing TPM factory
initialization which exercises this function in a child commit:

```
antirollback_read_space_firmware():566: TPM: Not initialized yet.
factory_initialize_tpm():530: TPM: factory initialization
tlcl_self_test_full: response is 0
tlcl_force_clear: response is 0
tlcl_define_space: response is 14c
define_space():197: define_space: kernel space already exists
tlcl_write: response is 0
tlcl_define_space: response is 14c
define_space():197: define_space: RO MRC Hash space already exists
tlcl_write: response is 0
tlcl_define_space: response is 14c
define_space():197: define_space: FWMP space already exists
tlcl_write: response is 0
tlcl_define_space: response is 0
tlcl_write: response is 0
tlcl_define_space: response is 0
tlcl_write: response is 0
tlcl_define_space: response is 0
tlcl_set_bits: response is 0
tlcl_define_space: response is 0
tlcl_write: response is 0
factory_initialize_tpm():553: TPM: factory initialization successful
```

BUG=b:184676425
BRANCH=None
TEST=With other changes, create a NVMEM space in a TPM 2.0 TPM with the
bits attribute.  Issue the command and verify that the TPM command
succeeds.

Signed-off-by: Aseda Aboagye <aaboagye@google.com>
Change-Id: I6ca6376bb9f7ed8fd1167c2c80f1e8d3c3f46653
Reviewed-on: https://review.coreboot.org/c/coreboot/+/55241
Reviewed-by: Aaron Durbin <adurbin@chromium.org>
Reviewed-by: Bob Moragues <moragues@google.com>
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
diff --git a/src/security/tpm/tss/tcg-2.0/tss_marshaling.c b/src/security/tpm/tss/tcg-2.0/tss_marshaling.c
index f21fe3d..83fff5f 100644
--- a/src/security/tpm/tss/tcg-2.0/tss_marshaling.c
+++ b/src/security/tpm/tss/tcg-2.0/tss_marshaling.c
@@ -197,6 +197,18 @@
 	return rc;
 }
 
+static int marshal_nv_setbits(struct obuf *ob,
+			      const struct tpm2_nv_setbits_cmd *command_body)
+{
+	int rc = 0;
+	const uint32_t handles[] = { TPM_RH_PLATFORM, command_body->nvIndex };
+
+	rc |= marshal_common_session_header(ob, handles, ARRAY_SIZE(handles));
+	rc |= obuf_write_be64(ob, command_body->bits);
+
+	return rc;
+}
+
 static int marshal_nv_write(struct obuf *ob,
 			    const struct tpm2_nv_write_cmd *command_body)
 {
@@ -386,6 +398,10 @@
 		rc |= marshal_nv_define_space(ob, tpm_command_body);
 		break;
 
+	case TPM2_NV_SetBits:
+		rc |= marshal_nv_setbits(ob, tpm_command_body);
+		break;
+
 	case TPM2_NV_Write:
 		rc |= marshal_nv_write(ob, tpm_command_body);
 		break;
@@ -618,6 +634,7 @@
 	case TPM2_Clear:
 	case TPM2_ClearControl:
 	case TPM2_NV_DefineSpace:
+	case TPM2_NV_SetBits:
 	case TPM2_NV_Write:
 	case TPM2_NV_WriteLock:
 	case TPM2_PCR_Extend: