コード例 #1
0
ファイル: Sample-KeyImport.cs プロジェクト: rgl/TSS.MSR
        void DuplicateImportRsaSample(Tpm2 tpm, TestContext testCtx)
        {
            TpmAlgId nameAlg = Substrate.Random(TpmCfg.HashAlgs);
            var      policy  = new PolicyTree(nameAlg);

            policy.SetPolicyRoot(new TpmPolicyCommand(TpmCc.Duplicate));

            var inPub = new TpmPublic(nameAlg,
                                      ObjectAttr.Sign | ObjectAttr.AdminWithPolicy | ObjectAttr.SensitiveDataOrigin,
                                      policy.GetPolicyDigest(),
                                      new RsaParms(new SymDefObject(),
                                                   new SchemeRsassa(Substrate.Random(TpmCfg.HashAlgs)),
                                                   Substrate.Random(TpmCfg.RsaKeySizes), 0),
                                      new Tpm2bPublicKeyRsa());

            TpmHandle hKey = Substrate.CreateAndLoad(tpm, inPub, out TpmPublic pub);

            // Duplicate
            TpmPrivate priv = TpmHelper.GetPlaintextPrivate(tpm, hKey, policy);

            tpm.FlushContext(hKey);

            // Import
            TpmPrivate privImp = tpm.Import(Substrate.LoadRsaPrimary(tpm), null, pub, priv, null, new SymDefObject());
        } // SimpleDuplicateImportRsaSample
コード例 #2
0
ファイル: TestCertifyX509.cs プロジェクト: siyingpoof/TSS.MSR
        void TestCertifyX509_1(Tpm2 tpm, TestContext testCtx)
        {
            testCtx.ReportParams("Test phase: TestCertifyX509_1");

            var policy = new PolicyTree(TpmAlgId.Sha256);

            policy.SetPolicyRoot(new TpmPolicyCommand(TpmCc.CertifyX509));

            var keyTemplate = new TpmPublic(
                TpmAlgId.Sha256,
                ObjectAttr.Restricted | ObjectAttr.Sign | ObjectAttr.FixedParent | ObjectAttr.FixedTPM | ObjectAttr.UserWithAuth | ObjectAttr.AdminWithPolicy | ObjectAttr.SensitiveDataOrigin,
                policy.GetPolicyDigest(),
                new RsaParms(new SymDefObject(), new SchemeRsassa(TpmAlgId.Sha256), 2048, 0),
                new Tpm2bPublicKeyRsa()
                );

            // Make two keys
            TpmPublic certifyingKeyPub, keyToBeCertifiedPub;
            TpmHandle hCertifyingKey    = Substrate.CreatePrimary(tpm, keyTemplate, out certifyingKeyPub);
            TpmHandle hKeyToBeCertified = Substrate.CreatePrimary(tpm, keyTemplate, out keyToBeCertifiedPub);

            var partialCert      = CertifyX509Support.MakeExemplarPartialCert();
            var partialCertBytes = partialCert.GetDerEncoded();

            // If you want to paste in your own hex put it here and s
            //var partialCertBytes = Globs.ByteArrayFromHex("01020304");

            AuthSession sess = tpm.StartAuthSessionEx(TpmSe.Policy, TpmAlgId.Sha256);

            sess.RunPolicy(tpm, policy);

            // I used this to test that the auth is OK.  Of course you need to change the PolicyCommandCode above
            //var attestInfo = tpm[sess].Certify(hKeyToBeCertified, hCertifyingKey, new byte[0], new NullSigScheme(), out var legacySignature);

            byte[]          tbsHash;
            ISignatureUnion signature;

            byte[] addedTo     = tpm[sess].CertifyX509(hKeyToBeCertified, hCertifyingKey, new byte[0], new NullSigScheme(), partialCertBytes, out tbsHash, out signature);
            var    addedToCert = AddedToCertificate.FromDerEncoding(addedTo);

            var returnedCert = CertifyX509Support.AssembleCertificate(partialCert, addedToCert, ((SignatureRsa)signature).GetTpmRepresentation());

            // Does the expected hash match the returned hash?
            var tbsBytes        = returnedCert.GetTbsCertificate();
            var expectedTbsHash = TpmHash.FromData(TpmAlgId.Sha256, tbsBytes);

            Debug.Assert(Globs.ArraysAreEqual(expectedTbsHash.HashData, tbsHash));

            // If you get this far we can check the cert is properly signed but we'll need to do a
            // bit of TPM<->Bouncy Castle data type conversion.


            tpm.FlushContext(hCertifyingKey);
            tpm.FlushContext(hKeyToBeCertified);
        } // TestCertifyX509_1
コード例 #3
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
 /// <summary>
 /// This callback function provides authorization in plain text
 /// </summary>
 static public void PolicySecretCallback(
     PolicyTree policyTree,
     TpmPolicySecret ace,
     out SessionBase authorizingSession,
     out TpmHandle authorizedEntityHandle,
     out bool flushAuthEntity)
 {
     authorizingSession     = _publicAuthorizationValue;
     authorizedEntityHandle = _publicSealedObjectHandle;
     flushAuthEntity        = false;
 }
コード例 #4
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
        /// <summary>
        /// This callback function provides authorization in the form of an HMAC session
        /// </summary>
        static public void PolicySecretCallback2(
            PolicyTree policyTree,
            TpmPolicySecret ace,
            out SessionBase authorizingSession,
            out TpmHandle authorizedEntityHandle,
            out bool flushAuthEntity)
        {
            AuthSession s0 = _sharedTpm.StartAuthSessionEx(TpmSe.Hmac, TpmAlgId.Sha1);

            authorizingSession     = s0;
            authorizedEntityHandle = _publicSealedObjectHandle;
            flushAuthEntity        = true;
        }
コード例 #5
0
ファイル: TestCertifyX509.cs プロジェクト: rgl/TSS.MSR
        void TestCertifyX509(Tpm2 tpm, TestContext testCtx)
        {
            if (!TpmCfg.IsImplemented(TpmCc.CertifyX509))
            {
                Substrate.WriteToLog("TestCertifyX509 skipped", ConsoleColor.DarkCyan);
                return;
            }

            ObjectAttr attr = ObjectAttr.Restricted | ObjectAttr.Sign
                              | ObjectAttr.FixedParent | ObjectAttr.FixedTPM
                              | ObjectAttr.UserWithAuth | ObjectAttr.AdminWithPolicy
                              | ObjectAttr.SensitiveDataOrigin;

            var policy = new PolicyTree(TpmAlgId.Sha256);

            policy.SetPolicyRoot(new TpmPolicyCommand(TpmCc.CertifyX509));

            var keyTemplateRsa = new TpmPublic(TpmAlgId.Sha256, attr, policy.GetPolicyDigest(),
                                               new RsaParms(new SymDefObject(), new SchemeRsassa(TpmAlgId.Sha256), 2048, 0),
                                               new Tpm2bPublicKeyRsa()
                                               );
            var keyTemplateEcc = new TpmPublic(TpmAlgId.Sha256, attr, policy.GetPolicyDigest(),
                                               new EccParms(new SymDefObject(), new SchemeEcdsa(TpmAlgId.Sha256),
                                                            EccCurve.NistP256, new NullKdfScheme()),
                                               new EccPoint()
                                               );
            var keyTemplatePss = new TpmPublic(TpmAlgId.Sha256, attr, policy.GetPolicyDigest(),
                                               new RsaParms(new SymDefObject(), new SchemeRsapss(TpmAlgId.Sha256), 2048, 0),
                                               new Tpm2bPublicKeyRsa()
                                               );

            TestCertifyX509Impl(tpm, testCtx, keyTemplateRsa, keyTemplateRsa, policy, "RsaWithRsa.1");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateRsa, keyTemplateEcc, policy, "RsaWithEcc.1");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateEcc, keyTemplateEcc, policy, "EccWithEcc.1");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateEcc, keyTemplateRsa, policy, "EccWithRsa.1");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateRsa, keyTemplatePss, policy, "RsaWithPss.1");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateEcc, keyTemplatePss, policy, "EccWithPss.1");

            attr &= ~(ObjectAttr.Restricted | ObjectAttr.FixedParent | ObjectAttr.FixedTPM);
            keyTemplateRsa.objectAttributes = attr;
            keyTemplateEcc.objectAttributes = attr;
            keyTemplatePss.objectAttributes = attr;
            TestCertifyX509Impl(tpm, testCtx, keyTemplateRsa, keyTemplateRsa, policy, "RsaWithRsa.2");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateRsa, keyTemplateEcc, policy, "RsaWithEcc.2");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateEcc, keyTemplateEcc, policy, "EccWithEcc.2");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateEcc, keyTemplateRsa, policy, "EccWithRsa.2");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateRsa, keyTemplatePss, policy, "RsaWithPss.2");
            TestCertifyX509Impl(tpm, testCtx, keyTemplateEcc, keyTemplatePss, policy, "EccWithPss.2");
        } // TestCertifyX509
コード例 #6
0
        public static TpmPrivate GetPlaintextPrivate(Tpm2 tpm, TpmHandle key, PolicyTree policy)
        {
            AuthSession sess = tpm.StartAuthSessionEx(TpmSe.Policy, policy.HashAlg);

            sess.RunPolicy(tpm, policy);
            TpmPrivate privPlain = null;

            byte[] symSeed;
            tpm[sess]._ExpectResponses(TpmRc.Success, TpmRc.Attributes)
            .Duplicate(key, TpmRh.Null, null, new SymDefObject(),
                       out privPlain, out symSeed);
            Debug.Assert(!tpm._LastCommandSucceeded() || symSeed.Length == 0);
            tpm.FlushContext(sess);
            return(Globs.IsEmpty(privPlain.buffer) ? null : privPlain);
        }
コード例 #7
0
ファイル: Sample-AikActivation.cs プロジェクト: rgl/TSS.MSR
        void ActivateAikSample(Tpm2 tpm, TestContext testCtx)
        {
            // Use an RSA primary key in the Endorsement hierarchy (EK) to 'activate'
            // another primary in the Endorsement hierarchy (AIK).

            // Note: this procedure can be used to activate a key in the Storage hierarchy, too.

            // "Activation" means secure passing sensitive data generated by a CA (e.g.
            // a symmetric key protecting a freshly generated certificate), so that only
            // a device with the TPM owning the target AIK and EK can access these data.

            // Create a primary key that we will certify.

            //////////////////////////////////////////////////////////////////////////////
            // Device side code
            //////////////////////////////////////////////////////////////////////////////

            // Name algorithm of the new AIK
            TpmAlgId nameAlg = TpmAlgId.Sha256;

            // The key to be certified needs a policy. It can be ANY policy, but here
            // it is configured to allow AIK usage only with the following commands
            var policyAIK = new PolicyTree(nameAlg);
            var policyOR  = new TpmPolicyOr();

            policyAIK.SetPolicyRoot(policyOR);
            policyOR.AddPolicyBranch(new TpmPolicyCommand(TpmCc.ActivateCredential, "Activate"));
            policyOR.AddPolicyBranch(new TpmPolicyCommand(TpmCc.Certify, "Certify"));
            policyOR.AddPolicyBranch(new TpmPolicyCommand(TpmCc.CertifyCreation, "CertifyCreation"));
            policyOR.AddPolicyBranch(new TpmPolicyCommand(TpmCc.Quote, "Quote"));

            var inAIKPub = new TpmPublic(nameAlg,
                                         ObjectAttr.Restricted | ObjectAttr.Sign | ObjectAttr.FixedParent | ObjectAttr.FixedTPM
                                         | ObjectAttr.AdminWithPolicy | ObjectAttr.SensitiveDataOrigin,
                                         policyAIK.GetPolicyDigest(),
                                         new RsaParms(new SymDefObject(), new SchemeRsassa(TpmAlgId.Sha256), 2048, 0),
                                         new Tpm2bPublicKeyRsa());

            TpmPublic    AIKpub;
            var          inSens = new SensitiveCreate(Substrate.RandomAuth(nameAlg), null);
            CreationData creationData;

            byte[]     creationHash;
            TkCreation creationTk;
            TpmHandle  hAIK = tpm.CreatePrimary(TpmRh.Endorsement, inSens, inAIKPub, null, null, out AIKpub,
                                                out creationData, out creationHash, out creationTk);
            // An alternative using test substrate helper
            //TpmHandle hAIK = Substrate.CreatePrimary(tpm, inAIKPub, TpmRh.Endorsement);

            // Normally a device would have a pre-provisioned persistent EK with the above handle
            TpmHandle hEK = new TpmHandle(0x81010001);

            // Get its public part
            TpmPublic EKpub = null;

            // In a test environment the real EK may be absent. In this case use
            // a primary key temporarily created in the Endorsement hierarchy.
            byte[] name, qname;
            tpm._AllowErrors()
            .ReadPublic(hEK, out name, out qname);
            if (!tpm._LastCommandSucceeded())
            {
                var inEKpub = new TpmPublic(TpmAlgId.Sha256,
                                            ObjectAttr.Restricted | ObjectAttr.Decrypt | ObjectAttr.FixedParent | ObjectAttr.FixedTPM
                                            | ObjectAttr.AdminWithPolicy | ObjectAttr.SensitiveDataOrigin,
                                            new byte[] { 0x83, 0x71, 0x97, 0x67, 0x44, 0x84, 0xb3, 0xf8,
                                                         0x1a, 0x90, 0xcc, 0x8d, 0x46, 0xa5, 0xd7, 0x24,
                                                         0xfd, 0x52, 0xd7, 0x6e, 0x06, 0x52, 0x0b, 0x64,
                                                         0xf2, 0xa1, 0xda, 0x1b, 0x33, 0x14, 0x69, 0xaa },
                                            new RsaParms(new SymDefObject(TpmAlgId.Aes, 128, TpmAlgId.Cfb), null, 2048, 0),
                                            new Tpm2bPublicKeyRsa());

                inSens = new SensitiveCreate(null, null);
                hEK    = tpm.CreatePrimary(TpmRh.Endorsement, inSens, inEKpub, null, null, out EKpub,
                                           out creationData, out creationHash, out creationTk);
            }

            // Marshal public parts of AIK and EK

            byte[] AIKpubBytes = AIKpub.GetTpmRepresentation();
            byte[] EKpubBytes  = EKpub.GetTpmRepresentation();

            // Here the device uses network to pass AIKpubBytes and EKpubBytes (as well as
            // the EK certificate) to CA service.


            //////////////////////////////////////////////////////////////////////////////
            // Service (CA) side code
            //////////////////////////////////////////////////////////////////////////////

            // Unmarshal AIKpub and EKpub (and EK certificate)

            var m = new Marshaller(AIKpubBytes);

            AIKpub = m.Get <TpmPublic>();
            m      = new Marshaller(EKpubBytes);
            EKpub  = m.Get <TpmPublic>();

            // Symmetric key to be used by CA to encrypt the new certificate it creates for AIK
            byte[] secretKey = Substrate.RandomBytes(32);

            // Here CA does the following (the sample does not show this code):
            // - Validates EK certificate
            // - Generates a new certificate for AIK (AIKcert)
            // - Encrypts AIKcert with secretKey

            // Create an activation blob

            // Internal wrapper key encrypted with EKpub to be used by TPM2_ActivateCredential() command.
            byte[] encSecret;

            // An encrypted and HMACed object tied to the destination TPM. It contains
            // 'secret' to be extracted by the successful TPM2_ActivateCredential() command
            // (that can only succeeed on the TPM that originated both EK and AIK).
            IdObject certInfo;

            // Run TSS.Net equivalent of TPM2_MakeCredential() command (convenient for the server side,
            // as it will likely be faster than the TPM transaction and allows concurrent execution).
            certInfo = EKpub.CreateActivationCredentials(secretKey, AIKpub.GetName(), out encSecret);

            // Marshal certInfo

            // IdObject data type requires customized marshaling
            m = new Marshaller();
            m.Put(certInfo.integrityHMAC.Length, "integrityHMAC.Length");
            m.Put(certInfo.integrityHMAC, "integrityHMAC");
            m.Put(certInfo.encIdentity.Length, "encIdentity");
            m.Put(certInfo.encIdentity, "encIdentity.Length");
            byte[] certInfoBytes = m.GetBytes();

            // Here the CA passes certInfoBytes and encSecret (as well as the encrypted
            // AIK certificate) back to the device via network.


            //////////////////////////////////////////////////////////////////////////////
            // Device side code again
            //////////////////////////////////////////////////////////////////////////////

            // Unmarshal certInfo and encSecret (and encrypted AIK certificate)

            m = new Marshaller(certInfoBytes);
            int len = m.Get <int>();

            certInfo.integrityHMAC = m.GetArray <byte>(len);
            len = m.Get <int>();
            certInfo.encIdentity = m.GetArray <byte>(len);
            // encSecret is a byte array, so, normally, no special unmarshalling is required

            // Create policy session to authorize AIK usage
            AuthSession sessAIK = tpm.StartAuthSessionEx(TpmSe.Policy, nameAlg);

            sessAIK.RunPolicy(tpm, policyAIK, "Activate");

            // Create policy description and corresponding policy session to authorize EK usage
            var policyEK = new PolicyTree(EKpub.nameAlg);

            policyEK.SetPolicyRoot(new TpmPolicySecret(TpmRh.Endorsement, false, 0, null, null));

            AuthSession sessEK = tpm.StartAuthSessionEx(TpmSe.Policy, EKpub.nameAlg);

            sessEK.RunPolicy(tpm, policyEK);

            byte[] recoveredSecretKey = tpm[sessAIK, sessEK].ActivateCredential(hAIK, hEK, certInfo, encSecret);

            testCtx.AssertEqual("Secret.1", recoveredSecretKey, secretKey);

            // Here the device can use recoveredSecretKey to decrypt the AIK certificate

            //////////////////////////////////////////////////////////////////////////////
            // End of activation sequence
            //////////////////////////////////////////////////////////////////////////////


            //
            // Now prepare activation using the TPM built-in command
            //

            byte[]   encSecret2 = null;
            IdObject certInfo2  = tpm.MakeCredential(hEK, secretKey, AIKpub.GetName(), out encSecret2);

            // Reinitialize policy sessions
            tpm.PolicyRestart(sessAIK);
            sessAIK.RunPolicy(tpm, policyAIK, "Activate");
            tpm.PolicyRestart(sessEK);
            sessEK.RunPolicy(tpm, policyEK);

            recoveredSecretKey = tpm[sessAIK, sessEK].ActivateCredential(hAIK, hEK, certInfo2, encSecret2);
            testCtx.AssertEqual("Secret.2", recoveredSecretKey, secretKey);

            // Cleanup
            tpm.FlushContext(sessAIK);
            tpm.FlushContext(sessEK);
            tpm.FlushContext(hAIK);

            if (hEK.handle != 0x81010001)
            {
                tpm.FlushContext(hEK);
            }
        } // ActivateAikSample
コード例 #8
0
        /// <summary>
        /// Activates an identity key within the TPM device.
        /// </summary>
        /// <param name="encryptedKey">The encrypted identity key.</param>
        public override void ActivateIdentityKey(byte[] encryptedKey)
        {
            if (Logging.IsEnabled)
            {
                Logging.Enter(this, $"{encryptedKey}", nameof(ActivateIdentityKey));
            }
            Destroy();

            // Take the pieces out of the container
            var           m      = new Marshaller(encryptedKey, DataRepresentation.Tpm);
            Tpm2bIdObject cred2b = m.Get <Tpm2bIdObject>();

            byte[] encryptedSecret = new byte[m.Get <ushort>()];
            encryptedSecret = m.GetArray <byte>(encryptedSecret.Length, "encryptedSecret");
            TpmPrivate dupBlob = m.Get <TpmPrivate>();

            byte[] encWrapKey = new byte[m.Get <ushort>()];
            encWrapKey = m.GetArray <byte>(encWrapKey.Length, "encWrapKey");
            UInt16 pubSize = m.Get <UInt16>();

            _idKeyPub = m.Get <TpmPublic>();
            byte[] cipherText = new byte[m.Get <ushort>()];
            cipherText = m.GetArray <byte>(cipherText.Length, "uriInfo");

            // Setup the authorization session for the EK
            var policyNode = new TpmPolicySecret(TpmHandle.RhEndorsement, false, 0, Array.Empty <byte>(), Array.Empty <byte>());
            var policy     = new PolicyTree(_ekPub.nameAlg);

            policy.SetPolicyRoot(policyNode);
            AuthSession ekSession = _tpm2.StartAuthSessionEx(TpmSe.Policy, _ekPub.nameAlg);

            ekSession.RunPolicy(_tpm2, policy);

            // Perform the activation
            ekSession.Attrs  &= ~SessionAttr.ContinueSession;
            _activationSecret = _tpm2[Array.Empty <byte>(), ekSession].ActivateCredential(
                new TpmHandle(TPM_20_SRK_HANDLE),
                new TpmHandle(TPM_20_EK_HANDLE),
                cred2b.credential,
                encryptedSecret);

            TpmPrivate importedKeyBlob = _tpm2.Import(
                new TpmHandle(TPM_20_SRK_HANDLE),
                _activationSecret,
                _idKeyPub,
                dupBlob,
                encWrapKey,
                new SymDefObject(TpmAlgId.Aes, 128, TpmAlgId.Cfb));

            _idKeyHandle = _tpm2.Load(new TpmHandle(TPM_20_SRK_HANDLE), importedKeyBlob, _idKeyPub);

            // Persist the key in NV
            TpmHandle hmacKeyHandle = new TpmHandle(AIOTH_PERSISTED_KEY_HANDLE);

            _tpm2.EvictControl(new TpmHandle(TpmRh.Owner), _idKeyHandle, hmacKeyHandle);

            // Unload the transient copy from the TPM
            _tpm2.FlushContext(_idKeyHandle);
            _idKeyHandle = hmacKeyHandle;

            if (Logging.IsEnabled)
            {
                Logging.Exit(this, $"{encryptedKey}", nameof(ActivateIdentityKey));
            }
        }
コード例 #9
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
        /// <summary>
        /// Some policies can be evaluated solely from public parts of the policy.
        /// Others needs a private keyholder to sign some data. Tpm2Lib provides
        /// a callback facility for these cases.
        ///
        /// This second sample illustrates the use of callbacks to provide authData.
        /// </summary>
        /// <param name="tpm">Reference to the TPM object to use.</param>
        static void PolicyEvaluationWithCallback2(Tpm2 tpm)
        {
            Console.WriteLine("Policy evaluation with callback sample 2.");

            //
            // Check if policy commands are implemented by TPM. This list
            // could include all the other used commands as well.
            // This check here makes sense for policy commands, because
            // usually a policy has to be executed in full. If a command
            // out of the chain of policy commands is not implemented in the
            // TPM, the policy cannot be satisfied.
            //
            var usedCommands = new[] {
                TpmCc.PolicySecret,
                TpmCc.PolicyGetDigest,
                TpmCc.PolicyRestart
            };

            foreach (var commandCode in usedCommands)
            {
                if (!tpm.Helpers.IsImplemented(commandCode))
                {
                    Console.WriteLine("Cancel Policy evaluation callback 2 sample, because command {0} is not implemented by TPM.", commandCode);
                    return;
                }
            }

            //
            // Create an object with an AuthValue. The type of object is immaterial
            // (it can even be the owner). In order to construct the policy we will
            // need the name and to prove that we know the AuthVal.
            //
            _publicAuthorizationValue = AuthValue.FromRandom(10);
            var dataToSeal = new byte[] { 1, 2, 3, 4 };

            _publicSealedObjectHandle = CreateSealedPrimaryObject(tpm,
                                                                  dataToSeal,
                                                                  _publicAuthorizationValue,
                                                                  null);
            byte[] objectName = _publicSealedObjectHandle.Name;

            var policy = new PolicyTree(TpmAlgId.Sha256);

            policy.Create(
                new PolicyAce[]
            {
                new TpmPolicySecret(objectName,                 // Name of the obj that we will prove authData
                                    true,                       // Include nonceTpm
                                    new byte[0],                // Not bound to a cpHash
                                    new byte[0],                // Null policyRef
                                    0),                         // Never expires (in this session)
                "leaf"                                          // Name for this ACE
            });

            TpmHash expectedHash = policy.GetPolicyDigest();

            //
            // We are about to ask for the session to be evaluated, but in order
            // to process TpmPolicySecret the caller will have to prove knowledge of
            // the authValue associated with objectName. In this first version we
            // do this with PWAP.
            //
            policy.SetPolicySecretCallback(PolicySecretCallback);
            AuthSession authSession = tpm.StartAuthSessionEx(TpmSe.Policy, TpmAlgId.Sha256);

            authSession.RunPolicy(tpm, policy, "leaf");

            //
            // The policy evaluated.  But is the digest what we expect?
            //
            byte[] digestIs = tpm.PolicyGetDigest(authSession.Handle);
            if (expectedHash != digestIs)
            {
                throw new Exception("Incorrect PolicyDigest");
            }

            //
            // And now do the same thing but with an HMAC session.
            //
            _sharedTpm = tpm;
            tpm.PolicyRestart(authSession.Handle);
            policy.SetPolicySecretCallback(PolicySecretCallback2);
            authSession.RunPolicy(tpm, policy, "leaf");
            _sharedTpm = null;

            //
            // The policy evaluated. But is the digest what we expect?
            //
            digestIs = tpm.PolicyGetDigest(authSession.Handle);
            if (expectedHash != digestIs)
            {
                throw new Exception("Incorrect PolicyDigest");
            }
            Console.WriteLine("TpmPolicySignature evaluated.");

            tpm.FlushContext(authSession.Handle);
        }
コード例 #10
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
        /// <summary>
        /// Some policies can be evaluated solely from public parts of the policy.
        /// Others need a private keyholder to sign some data. Tpm2Lib provides a
        /// callback facility for these cases. In this sample the callback
        /// signs some data using a software key. But the callback might also
        /// ask for a smartcard to sign a challenge, etc.
        /// </summary>
        /// <param name="tpm">reference to the TPM2 object to use.</param>
        static void PolicyEvaluationWithCallback(Tpm2 tpm)
        {
            Console.WriteLine("Policy evaluation with callback sample.");

            //
            // Check if policy commands are implemented by TPM. This list
            // could include all the other used commands as well.
            // This check here makes sense for policy commands, because
            // usually a policy has to be executed in full. If a command
            // out of the chain of policy commands is not implemented in the
            // TPM, the policy cannot be satisfied.
            //
            var usedCommands = new[] {
                TpmCc.PolicySigned,
                TpmCc.PolicyGetDigest
            };

            foreach (var commandCode in usedCommands)
            {
                if (!tpm.Helpers.IsImplemented(commandCode))
                {
                    Console.WriteLine("Cancel Policy evaluation callback sample, because command {0} is not implemented by TPM.", commandCode);
                    return;
                }
            }

            //
            // Template for a software signing key
            //
            var signKeyPublicTemplate = new TpmPublic(TpmAlgId.Sha256,
                                                      ObjectAttr.Sign | ObjectAttr.Restricted,
                                                      new byte[0],
                                                      new RsaParms(SymDefObject.NullObject(),
                                                                   new SchemeRsassa(TpmAlgId.Sha1),
                                                                   2048, 0),
                                                      new Tpm2bPublicKeyRsa());

            //
            // Create a new random key
            //
            _publicSigningKey = new AsymCryptoSystem(signKeyPublicTemplate);

            //
            // Create a policy containing a TpmPolicySigned referring to the new
            // software signing key.
            //
            _expectedExpirationTime = 60;
            var policy = new PolicyTree(TpmAlgId.Sha256);

            policy.Create(
                new PolicyAce[]
            {
                new TpmPolicySigned(_publicSigningKey.GetPublicParms().GetName(),
                                                               // Newly created PubKey
                                    true,                      // nonceTpm required, expiration time is given
                                    _expectedExpirationTime,   // expirationTime for policy
                                    new byte[0],               // cpHash
                                    new byte[] { 1, 2, 3, 4 }) // policyRef
                {
                    NodeId = "Signing Key 1"
                },                                                          // Distinguishing name
                new TpmPolicyChainId("leaf")                                // Signed data
            });

            //
            // Compute the expected hash for the policy session. This hash would be
            // used in the object associated with the policy to confirm that the
            // policy is actually fulfilled.
            //
            TpmHash expectedHash = policy.GetPolicyDigest();

            //
            // The use of the object associated with the policy has to evaluate the
            // policy. In order to process TpmPolicySigned the caller will have to
            // sign a data structure challenge from the TPM. Here we install a
            // callback that will sign the challenge from the TPM.
            //
            policy.SetSignerCallback(SignerCallback);

            //
            // Evaluate the policy. Tpm2Lib will traverse the policy tree from leaf to
            // root (in this case just TpmPolicySigned) and will call the signer callback
            // to get a properly-formed challenge signed.
            //
            AuthSession authSession = tpm.StartAuthSessionEx(TpmSe.Policy, TpmAlgId.Sha256);

            authSession.RunPolicy(tpm, policy, "leaf");

            //
            // And check that the TPM policy hash is what we expect
            //
            byte[] actualHash = tpm.PolicyGetDigest(authSession.Handle);

            if (expectedHash != actualHash)
            {
                throw new Exception("Policy evaluation error");
            }

            Console.WriteLine("TpmPolicySignature evaluated.");

            //
            // Clean up
            //
            tpm.FlushContext(authSession.Handle);
        }
コード例 #11
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
        /// <summary>
        /// The callback to sign the TpmPolicySignature challenge from the TPM.
        /// </summary>
        /// <param name="policyTree">The policy tree to check.</param>
        /// <param name="ace">The policy element (TpmPolicySignature) to evaluate.</param>
        /// <param name="nonceTpm">The nonce from the TPM.</param>
        /// <returns>Signature of the nonce.</returns>
        public static ISignatureUnion SignerCallback(PolicyTree policyTree, TpmPolicySigned ace,
                                                     byte[] nonceTpm, out TpmPublic verificationKey)
        {
            //
            // This function checks the parameters of the associated TpmPolicySigned
            // ACE, and if they are those expected the TPM challenge is signed.
            // Note that policy expressions are often obtained from untrustworthy
            // sources, so it is important for key-holders to check what they
            // are bing asked to do before signing anything.
            //

            //
            // The policy just contains the name of the signature verification key, however the
            // TPM needs the actual public key to verify the signature.  Check that the name
            // matches, and if it does return the public key.
            //
            byte[] expectedName = _publicSigningKey.GetPublicParms().GetName();
            if (!expectedName.SequenceEqual(ace.AuthObjectName))
            {
                throw new Exception("Unexpected name in policy.");
            }
            verificationKey = _publicSigningKey.GetPublicParms();

            //
            // Check that the key is the one that we expect
            //
            if (ace.NodeId != "Signing Key 1")
            {
                throw new Exception("Unrecognized key");
            }


            //
            // Check that nonceTom is not null (otherwise anything we sign can
            // be used for any session).
            //
            if (nonceTpm.Length == 0)
            {
                throw new Exception("Sign challenges with expiration time need nonce.");
            }

            //
            // Check PolicyRef and cpHash are what we want to sign
            //
            if (ace.CpHash.Length != 0)
            {
                throw new Exception("I only sign null-cpHash");
            }

            if (!ace.PolicyRef.SequenceEqual(new byte[] { 1, 2, 3, 4 }))
            {
                throw new Exception("Incorrect PolicyRef");
            }

            //
            // And finally check that the expiration is set correctly. Check for
            // positive values (simple signing policy) and negative values (sining
            // policy with ticket).
            //
            if (ace.ExpirationTime != _expectedExpirationTime)
            {
                throw new Exception("Unexpected expiration time");
            }

            //
            // Everything is OK, so get a formatted bloc containing the challenge
            // data and then sign it.
            //
            byte[] dataStructureToSign = PolicyTree.GetDataStructureToSign(ace.ExpirationTime,
                                                                           nonceTpm,
                                                                           ace.CpHash,
                                                                           ace.PolicyRef);
            ISignatureUnion signature = _publicSigningKey.Sign(dataStructureToSign);

            return(signature);
        }
コード例 #12
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
        /// <summary>
        /// This sample demonstrates how policies can be created in a standard
        /// form and then shared between hosts.
        /// </summary>
        static void PolicySerialization()
        {
            Console.WriteLine("Policy serialization and de-serialization sample:");

            //
            // Create a policy session with two branches
            //
            var policy0 = new PolicyTree(TpmAlgId.Sha256);

            policy0.CreateNormalizedPolicy(new[] {
                new PolicyAce[]
                {
                    new TpmPolicyPassword(),
                    //
                    // We can use an unsupported command when only serializing
                    // and deserializing. Execution of the policy might fail.
                    //
                    new TpmPolicyLocality(LocalityAttr.TpmLocZero),
                    new TpmPolicyChainId("branch_1")
                },
                new PolicyAce[]
                {
                    new TpmPolicyPassword(),
                    new TpmPolicyCommand(TpmCc.ChangeEPS),
                    "branch_2"
                }
            });

            //
            // And save it to disk as XML
            //
            const string fileName = "PolicySerialization.xml";

            policy0.SerializeToFile("Test Policy", PolicySerializationFormat.Xml, fileName);

            //
            // Now recover it into a new session
            //
            var policy1 = new PolicyTree(TpmAlgId.Sha256);

            policy1.DeserializeFromFile(PolicySerializationFormat.Xml, fileName);

            //
            // And check that the two policies are the same
            //
            if (policy0.GetPolicyDigest() != policy1.GetPolicyDigest())
            {
                throw new Exception("Policy library error");
            }

            Console.WriteLine("Serialized policy to {0}.", fileName);

            //
            // And now do the same, but serialized to JSON
            //
            const string fileNameJ = "PolicySerialization.json";

            policy0.SerializeToFile("Test Policy", PolicySerializationFormat.Json, fileNameJ);

            //
            // Now recover it into a new session
            //
            var policy1J = new PolicyTree(TpmAlgId.Sha256);

            policy1J.DeserializeFromFile(PolicySerializationFormat.Json, fileNameJ);

            //
            // And check that the two policies are the same
            //
            if (policy0.GetPolicyDigest() != policy1J.GetPolicyDigest())
            {
                throw new Exception("Policy library error");
            }

            Console.WriteLine("Serialized policy to {0}.", fileNameJ);
        }
コード例 #13
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
        /// <summary>
        /// This sample illustrates the use of a TpmPolicyOr.
        /// </summary>
        static void PolicyOr(Tpm2 tpm)
        {
            Console.WriteLine("PolicyOr sample:");

            //
            // Check if policy commands are implemented by TPM. This list
            // could include all the other used commands as well.
            // This check here makes sense for policy commands, because
            // usually a policy has to be executed in full. If a command
            // out of the chain of policy commands is not implemented in the
            // TPM, the policy cannot be satisfied.
            //
            var usedCommands = new[] {
                TpmCc.PolicyPCR,
                TpmCc.PolicyAuthValue
            };

            foreach (var commandCode in usedCommands)
            {
                if (!tpm.Helpers.IsImplemented(commandCode))
                {
                    Console.WriteLine("Cancel Policy OR sample, because command {0} is not implemented by TPM.", commandCode);
                    return;
                }
            }

            var pcrs = new uint[] { 1, 2, 3 };
            var sel  = new PcrSelection(TpmAlgId.Sha, pcrs);

            PcrSelection[] selOut;
            Tpm2bDigest[]  pcrValues;

            //
            // First read the PCR values
            //
            tpm.PcrRead(new[] { sel }, out selOut, out pcrValues);

            //
            // Save the current PCR values in a convenient data structure
            //
            var expectedPcrVals = new PcrValueCollection(selOut, pcrValues);

            //
            // Tpm2Lib encapsulates a set of policy assertions as the PolicyTree class.
            //
            var policy = new PolicyTree(TpmAlgId.Sha256);

            //
            // First branch of PolicyOr
            //
            var branch1 = new PolicyAce[]
            {
                new TpmPolicyPcr(expectedPcrVals),
                "branch_1"
            };

            //
            // Second branch of PolicyOr
            //
            var branch2 = new PolicyAce[]
            {
                new TpmPolicyAuthValue(),
                "branch_2"
            };

            //
            // Create the policy. CreateNormalizedPolicy takes an array-of-arrays
            // of PolicyACEs that are to be OR'ed together (the branches themselves cannot
            // contain TpmPOlicyOrs). The library code constructs a policy tree with
            // minimum number of TpmPolicyOrs at the root.
            //
            policy.CreateNormalizedPolicy(new[] { branch1, branch2 });

            //
            // Ask Tpm2Lib for the expected policy-hash for this policy
            //
            TpmHash expectedPolicyHash = policy.GetPolicyDigest();

            //
            // Create a sealed primary object with the policy-hash we just calculated
            //
            var       dataToSeal = new byte[] { 1, 2, 3, 4, 5, 4, 3, 2, 1 };
            var       authVal    = new byte[] { 1, 2 };
            TpmHandle primHandle = CreateSealedPrimaryObject(tpm,
                                                             dataToSeal,
                                                             authVal,
                                                             expectedPolicyHash.HashData);
            //
            // Create an actual TPM policy session to evaluate the policy
            //
            AuthSession session = tpm.StartAuthSessionEx(TpmSe.Policy, TpmAlgId.Sha256);

            //
            // Run the policy on the TPM
            //
            session.RunPolicy(tpm, policy, "branch_1");

            //
            // And unseal the object
            //
            byte[] unsealedData = tpm[session].Unseal(primHandle);
            Console.WriteLine("Unsealed data for branch_1: " + BitConverter.ToString(unsealedData));

            //
            // Now run the other branch
            //
            tpm.PolicyRestart(session.Handle);
            session.RunPolicy(tpm, policy, "branch_2");

            //
            // And the session will be unusable
            //
            unsealedData = tpm[session].Unseal(primHandle);
            Console.WriteLine("Unsealed data for branch_2: " + BitConverter.ToString(unsealedData));

            //
            // Clean up
            //
            tpm.FlushContext(session.Handle);
            tpm.FlushContext(primHandle);
        }
コード例 #14
0
ファイル: Program.cs プロジェクト: fars/TSS.MSR
        /// <summary>
        /// This sample illustrates the use of a simple TPM policy session. The policy demands
        /// PCR 1, 2, 3 set to current values, and the command be issued at locality zero.
        /// </summary>
        static void SimplePolicy(Tpm2 tpm)
        {
            Console.WriteLine("Simple Policy sample:");

            //
            // Check if policy commands are implemented by TPM. This list
            // could include all the other used commands as well.
            // This check here makes sense for policy commands, because
            // usually a policy has to be executed in full. If a command
            // out of the chain of policy commands is not implemented in the
            // TPM, the policy cannot be satisfied.
            //
            var usedCommands = new[] { TpmCc.PolicyPCR };

            foreach (var commandCode in usedCommands)
            {
                if (!tpm.Helpers.IsImplemented(commandCode))
                {
                    Console.WriteLine("Cancel Simple Policy sample, because command {0} is not implemented by TPM.", commandCode);
                    return;
                }
            }

            //
            // First read the PCR values
            //
            var pcrs = new uint[] { 1, 2, 3 };
            var sel  = new PcrSelection(TpmAlgId.Sha, pcrs);

            PcrSelection[] selOut;
            Tpm2bDigest[]  pcrValues;

            tpm.PcrRead(new[] { sel }, out selOut, out pcrValues);

            Console.WriteLine("PCR Selections:\n");
            foreach (PcrSelection s in selOut)
            {
                Console.WriteLine(s.ToString());
            }

            Console.WriteLine("PCR Values:\n");
            foreach (var v in pcrValues)
            {
                Console.WriteLine(v.ToString());
            }

            //
            // Save the current PCR values in a convenient data structure
            //
            var expectedPcrVals = new PcrValueCollection(selOut, pcrValues);

            //
            // Tpm2Lib encapsulates a set of policy assertions as the PolicyTree class.
            //
            var policy = new PolicyTree(TpmAlgId.Sha256);

            //
            // Set the policy: Locality AND PolicyPcr. This form of CreatePOlicy
            // only creates a single chain. Note that all well-formed policy chains
            // must have leaf identifiers. Leaf identifiers are just strings that
            // are unique in a policy so that the framework can be told what
            // chain to evaluate.
            //
            policy.Create(
                new PolicyAce[]
            {
                new TpmPolicyPcr(expectedPcrVals),
                "leaf"
            }
                );

            //
            // Ask Tpm2Lib for the expected policy-hash for this policy
            //
            TpmHash expectedPolicyHash = policy.GetPolicyDigest();

            //
            // Create a sealed primary object with the policy-hash we just calculated
            //
            var       dataToSeal = new byte[] { 1, 2, 3, 4, 5, 4, 3, 2, 1 };
            TpmHandle primHandle = CreateSealedPrimaryObject(tpm,
                                                             dataToSeal,
                                                             null,
                                                             expectedPolicyHash.HashData);
            //
            // Create an actual TPM policy session to evaluate the policy
            //
            AuthSession session = tpm.StartAuthSessionEx(TpmSe.Policy, TpmAlgId.Sha256);

            //
            // Run the policy on the TPM
            //
            session.RunPolicy(tpm, policy, "leaf");

            //
            // Unseal the object
            //
            byte[] unsealedData = tpm[session].Unseal(primHandle);
            Console.WriteLine("Unsealed data: " + BitConverter.ToString(unsealedData));

            //
            // Change a PCR and make sure that the policy no longer works
            //
            var nullAuth = new AuthValue();

            tpm[nullAuth].PcrEvent(TpmHandle.Pcr(3), new byte[] { 1, 2, 3 });
            tpm.PolicyRestart(session.Handle);

            //
            // Run the policy again - an error will be returned
            //
            TpmRc policyError = session.RunPolicy(tpm, policy, null, true);

            //
            // And the session will be unusable
            //
            unsealedData = tpm[session]._ExpectError(TpmRc.PolicyFail).Unseal(primHandle);

            //
            // Clean up
            //
            tpm.FlushContext(session.Handle);
            tpm.FlushContext(primHandle);
        }
コード例 #15
0
        /// <summary>
        /// Activates a symmetric identity within the Hardware Security Module.
        /// </summary>
        /// <param name="activation">The authentication challenge key supplied by the service.</param>
        public override void ActivateSymmetricIdentity(byte[] activation)
        {
            Destroy();

            // Take the pieces out of the container
            var m = new Marshaller(activation, DataRepresentation.Tpm);

            byte[] credentialBlob = new byte[m.Get <ushort>()];
            credentialBlob = m.GetArray <byte>(credentialBlob.Length, "credentialBlob");
            byte[] encryptedSecret = new byte[m.Get <ushort>()];
            encryptedSecret = m.GetArray <byte>(encryptedSecret.Length, "encryptedSecret");
            TpmPrivate dupBlob = m.Get <TpmPrivate>();

            byte[] encWrapKey = new byte[m.Get <ushort>()];
            encWrapKey = m.GetArray <byte>(encryptedSecret.Length, "encWrapKey");
            UInt16 pubSize = m.Get <UInt16>();

            _idKeyPub = m.Get <TpmPublic>();
            byte[] cipherText = new byte[m.Get <ushort>()];
            cipherText = m.GetArray <byte>(cipherText.Length, "uriInfo");

            // Setup the authorization session for the EK
            var policyNode = new TpmPolicySecret(
                TpmHandle.RhEndorsement, _ekAuth ?? Array.Empty <byte>(),
                new AuthValue(),
                false,
                0,
                Array.Empty <byte>(),
                Array.Empty <byte>());

            var policy = new PolicyTree(_ekPub.nameAlg);

            policy.SetPolicyRoot(policyNode);
            AuthSession ekSession = _tpm2.StartAuthSessionEx(TpmSe.Policy, _ekPub.nameAlg);

            ekSession.RunPolicy(_tpm2, policy);

            // Perform the activation
            ekSession.Attrs  &= ~SessionAttr.ContinueSession;
            _activationSecret = _tpm2[Array.Empty <byte>(), ekSession].ActivateCredential(
                new TpmHandle(TPM_20_SRK_HANDLE),
                new TpmHandle(TPM_20_EK_HANDLE),
                credentialBlob,
                encryptedSecret);

            TpmPrivate importedKeyBlob = _tpm2.Import(
                new TpmHandle(TPM_20_SRK_HANDLE),
                _activationSecret,
                _idKeyPub,
                dupBlob,
                encWrapKey,
                new SymDefObject(TpmAlgId.Aes, 128, TpmAlgId.Cfb));

            _idKeyHandle = _tpm2.Load(new TpmHandle(TPM_20_SRK_HANDLE), importedKeyBlob, _idKeyPub);

            // Persist the key in NV
            TpmHandle hmacKeyHandle = new TpmHandle(AIOTH_PERSISTED_KEY_HANDLE);

            _tpm2.EvictControl(new TpmHandle(TpmRh.Owner), _idKeyHandle, hmacKeyHandle);

            // Unload the transient copy from the TPM
            _tpm2.FlushContext(_idKeyHandle);
            _idKeyHandle = hmacKeyHandle;

            // Unwrap the URI
            byte[] clearText = SymmCipher.Decrypt(
                new SymDefObject(TpmAlgId.Aes, 128, TpmAlgId.Cfb),
                _activationSecret,
                new byte[16],
                cipherText);

            UnicodeEncoding unicode = new UnicodeEncoding();
            string          uriData = unicode.GetString(clearText);
            int             idx     = uriData.IndexOf('/');

            if (idx > 0)
            {
                string hostName = uriData.Substring(0, idx);
                string deviceId = uriData.Substring(idx + 1);

                // Persist the URI
                ProvisionUri(hostName, deviceId);
            }
        }
コード例 #16
0
ファイル: TestCertifyX509.cs プロジェクト: rgl/TSS.MSR
        void TestCertifyX509Impl(Tpm2 tpm, TestContext testCtx,
                                 TpmPublic subjectTemplate, TpmPublic sigKeyTemplate,
                                 PolicyTree policy, string testLabel)
        {
            var partialCert      = X509Helpers.MakePartialCert(subjectTemplate);
            var partialCertBytes = partialCert.GetDerEncoded();

            // If you want to paste in your own hex put it here and s
            //var partialCertBytes = Globs.ByteArrayFromHex("01020304");

            // Certify RSA with RSA
            TpmPublic certifyingKeyPub, keyToBeCertifiedPub;
            TpmHandle hSigKey     = Substrate.CreatePrimary(tpm, sigKeyTemplate, out certifyingKeyPub);
            TpmHandle hSubjectKey = Substrate.CreatePrimary(tpm, subjectTemplate, out keyToBeCertifiedPub);

            AuthSession sess = tpm.StartAuthSessionEx(TpmSe.Policy, TpmAlgId.Sha256);

            sess.RunPolicy(tpm, policy);

            ISignatureUnion sig;

            byte[] tbsHash;
            byte[] addedTo = tpm[sess].CertifyX509(hSubjectKey, hSigKey,
                                                   null, new NullSigScheme(), partialCertBytes,
                                                   out tbsHash, out sig);

            tpm.FlushContext(sess);
            tpm.FlushContext(hSubjectKey);

            var             addedToCert  = AddedToCertificate.FromDerEncoding(addedTo);
            X509Certificate returnedCert = X509Helpers.AssembleCertificate(partialCert, addedToCert,
                                                                           sig is SignatureRsa ? ((SignatureRsa)sig).GetTpmRepresentation()
                                                        : ((SignatureEcc)sig).GetTpmRepresentation());

            // Does the expected hash match the returned hash?
            var tbsBytes        = returnedCert.GetTbsCertificate();
            var expectedTbsHash = TpmHash.FromData(TpmAlgId.Sha256, tbsBytes);

            Debug.Assert(Globs.ArraysAreEqual(expectedTbsHash.HashData, tbsHash));

            // Is the cert properly signed?
            if (TpmHelper.GetScheme(sigKeyTemplate).GetUnionSelector() != TpmAlgId.Rsapss)
            {
                // Software crypto layer does not support PSS
                bool sigOk = certifyingKeyPub.VerifySignatureOverHash(tbsHash, sig);
                if (sigKeyTemplate.type == TpmAlgId.Ecc)
                {
#if !__NETCOREAPP2__
                    // No ECC in .Net Core
                    testCtx.Assert("Sign" + testLabel, sigOk);
#endif
                }
                else
                {
                    testCtx.Assert("Sign" + testLabel, sigOk);
                }
            }
            tpm.VerifySignature(hSigKey, tbsHash, sig);

            tpm.FlushContext(hSigKey);
        }