Initial commit to seed TPM2.0 source code directory

LICENSE file text copied from TCG library specification. README
describes the procedure used to extract source code from parts 3 and 4
of the specification.

The python scripts and part{34}.txt files will be removed in the
following commits.

Change-Id: Ie281e6e988481831f33483053455e8aff8f3f75f
Signed-off-by: Vadim Bendebury <[email protected]>
diff --git a/PolicyLocality.c b/PolicyLocality.c
new file mode 100644
index 0000000..2114aa1
--- /dev/null
+++ b/PolicyLocality.c
@@ -0,0 +1,108 @@
+// This file was extracted from the TCG Published
+// Trusted Platform Module Library
+// Part 3: Commands
+// Family "2.0"
+// Level 00 Revision 01.16
+// October 30, 2014
+
+#include "InternalRoutines.h"
+#include "PolicyLocality_fp.h"
+//
+//     Limit a policy to a specific locality
+//
+//     Error Returns                       Meaning
+//
+//     TPM_RC_RANGE                        all the locality values selected by locality have been disabled by
+//                                         previous TPM2_PolicyLocality() calls.
+//
+TPM_RC
+TPM2_PolicyLocality(
+    PolicyLocality_In        *in                 // IN: input parameter list
+    )
+{
+    SESSION        *session;
+    BYTE            marshalBuffer[sizeof(TPMA_LOCALITY)];
+    BYTE            prevSetting[sizeof(TPMA_LOCALITY)];
+    UINT32          marshalSize;
+    BYTE           *buffer;
+    TPM_CC          commandCode = TPM_CC_PolicyLocality;
+    HASH_STATE      hashState;
+
+// Input Validation
+
+    // Get pointer to the session structure
+    session = SessionGet(in->policySession);
+
+    // Get new locality setting in canonical form
+    buffer = marshalBuffer;
+    marshalSize = TPMA_LOCALITY_Marshal(&in->locality, &buffer, NULL);
+
+    // Its an error if the locality parameter is zero
+    if(marshalBuffer[0] == 0)
+        return TPM_RC_RANGE + RC_PolicyLocality_locality;
+
+    // Get existing locality setting in canonical form
+    buffer = prevSetting;
+    TPMA_LOCALITY_Marshal(&session->commandLocality, &buffer, NULL);
+
+    // If the locality has previously been set
+    if(    prevSetting[0] != 0
+        // then the current locality setting and the requested have to be the same
+        // type (that is, either both normal or both extended
+        && ((prevSetting[0] < 32) != (marshalBuffer[0] < 32)))
+        return TPM_RC_RANGE + RC_PolicyLocality_locality;
+
+    // See if the input is a regular or extended locality
+    if(marshalBuffer[0] < 32)
+    {
+        // if there was no previous setting, start with all normal localities
+        // enabled
+        if(prevSetting[0] == 0)
+            prevSetting[0] = 0x1F;
+
+         // AND the new setting with the previous setting and store it in prevSetting
+         prevSetting[0] &= marshalBuffer[0];
+
+         // The result setting can not be 0
+         if(prevSetting[0] == 0)
+          return TPM_RC_RANGE + RC_PolicyLocality_locality;
+  }
+  else
+  {
+      // for extended locality
+      // if the locality has already been set, then it must match the
+      if(prevSetting[0] != 0 && prevSetting[0] != marshalBuffer[0])
+          return TPM_RC_RANGE + RC_PolicyLocality_locality;
+
+      // Setting is OK
+      prevSetting[0] = marshalBuffer[0];
+
+  }
+
+// Internal Data Update
+
+  // Update policy hash
+  // policyDigestnew = hash(policyDigestold || TPM_CC_PolicyLocality || locality)
+  // Start hash
+  CryptStartHash(session->authHashAlg, &hashState);
+
+  // add old digest
+  CryptUpdateDigest2B(&hashState, &session->u2.policyDigest.b);
+
+  // add commandCode
+  CryptUpdateDigestInt(&hashState, sizeof(TPM_CC), &commandCode);
+
+  // add input locality
+  CryptUpdateDigest(&hashState, marshalSize, marshalBuffer);
+
+  // complete the digest
+  CryptCompleteHash2B(&hashState, &session->u2.policyDigest.b);
+
+  // update session locality by unmarshal function. The function must succeed
+  // because both input and existing locality setting have been validated.
+  buffer = prevSetting;
+  TPMA_LOCALITY_Unmarshal(&session->commandLocality, &buffer,
+                          (INT32 *) &marshalSize);
+
+   return TPM_RC_SUCCESS;
+}