public void AsyncSignWithInvalidPassTest(KsiService service) { byte[] data = Encoding.UTF8.GetBytes("This is my document"); IDataHasher dataHasher = KsiProvider.CreateDataHasher(); dataHasher.AddData(data); DataHash dataHash = dataHasher.GetHash(); ManualResetEvent waitHandle = new ManualResetEvent(false); Exception ex = null; IKsiSignature signature = null; service.BeginSign(dataHash, delegate(IAsyncResult ar) { try { signature = service.EndSign(ar); } catch (Exception e) { ex = e; } finally { waitHandle.Set(); } }, null); Assert.IsTrue(waitHandle.WaitOne(10000), "Wait handle timed out."); Assert.IsNull(signature, "Signature should be null."); Assert.IsNotNull(ex, "Exception should not be null."); Assert.AreEqual("Server responded with error message. Status: 258; Message: The request could not be authenticated.", ex.Message); }
public void VerifyExtendedSignatureUsingPublicationsFile() { KSI.Ksi ksi = GetKsi(); // Read the existing signature, assume it is extended IKsiSignature signature = LoadExtendedSignature(); DataHash documentHash = KsiProvider.CreateDataHasher(signature.InputHash.Algorithm) .AddData(File.ReadAllBytes("Resources/infile.txt")) .GetHash(); // Do the verification and check the result VerificationPolicy policy = new PublicationBasedVerificationPolicy(); VerificationContext context = new VerificationContext(signature) { DocumentHash = documentHash, PublicationsFile = ksi.GetPublicationsFile(), }; VerificationResult verificationResult = policy.Verify(context); if (verificationResult.ResultCode == VerificationResultCode.Ok) { Console.WriteLine("VerifyExtendedSignatureUsingPublicationsFile > signature valid"); } else { Console.WriteLine("VerifyExtendedSignatureUsingPublicationsFile > verification failed with error > " + verificationResult.VerificationError); } }
public void BlockSignerGetUniSignaturesOfManyRandomHashesTest(Ksi ksi) { int k = 7; Random random = new Random(); IdentityMetadata metadata = new IdentityMetadata("test client id", "test machine id"); List <DataHash> hashes = new List <DataHash>(); byte[] buffer = new byte[10]; for (int i = 0; i < k; i++) { IDataHasher hasher = KsiProvider.CreateDataHasher(); random.NextBytes(buffer); hasher.AddData(buffer); hashes.Add(hasher.GetHash()); } BlockSigner blockSigner = new BlockSigner(GetHttpKsiService()); foreach (DataHash hash in hashes) { blockSigner.Add(hash, metadata); } IEnumerable <IKsiSignature> uniSignatures = blockSigner.Sign(); int n = 0; foreach (IKsiSignature signature in uniSignatures) { Verify(ksi, signature, hashes[n++]); } }
public void VerifyExtendedSignatureUsingDefaultPolicy() { // Create simple wrapper. KSI.Ksi ksi = GetKsi(); // Read the existing signature, assume it is extended IKsiSignature signature = LoadExtendedSignature(); DataHash documentHash = KsiProvider.CreateDataHasher(signature.InputHash.Algorithm) .AddData(File.ReadAllBytes("Resources/infile.txt")) .GetHash(); // Do the verification and check the result. // The signature is verified against given document hash and publications file (publications file is automatically downloaded by simple wrapper). VerificationResult verificationResult = ksi.Verify(signature, documentHash); if (verificationResult.ResultCode == VerificationResultCode.Ok) { Console.WriteLine("VerifyExtendedSignatureUsingDefaultPolicy > signature valid"); } else { Console.WriteLine("VerifyExtendedSignatureUsingDefaultPolicy > verification failed with error > " + verificationResult.VerificationError); } }
public void SignHashDirectly() { KSI.Ksi ksi = GetKsi(); // Compute the hash first, use the input stream to provide the data to save memory for // hashing very large documents // In this example we simply use an input stream from an array of bytes but in practice it // could be file input stream from a very large file (several GB) IDataHasher dataHasher = KsiProvider.CreateDataHasher(); using (MemoryStream stream = new MemoryStream()) { byte[] data = Encoding.UTF8.GetBytes("Imagine this is a large file"); stream.Write(data, 0, data.Length); stream.Seek(0, SeekOrigin.Begin); dataHasher.AddData(stream); } // Provide the signing method with the computed hash instead of document itself IKsiSignature signature = ksi.Sign(dataHasher.GetHash()); // Persist signature to file //using (FileStream stream = File.OpenRead("sample-file-for-signing.txt.ksig")) //{ // signature.WriteTo(stream); //} }
public void VerifyCalendarBasedUnextended() { IKsiSignature signature = LoadUnextendedSignature(); DataHash documentHash = KsiProvider.CreateDataHasher(signature.InputHash.Algorithm) .AddData(File.ReadAllBytes("Resources/infile.txt")) .GetHash(); VerificationPolicy policy = new CalendarBasedVerificationPolicy(); VerificationContext context = new VerificationContext(signature) { DocumentHash = documentHash, KsiService = GetKsiService(), }; VerificationResult verificationResult = policy.Verify(context); if (verificationResult.ResultCode == VerificationResultCode.Ok) { Console.WriteLine("VerifyCalendarBasedUnextended > signature valid"); } else { Console.WriteLine("VerifyCalendarBasedUnextended > signature verification failed with error > " + verificationResult.VerificationError); } }
public void VerifyUnextendedSignatureUsingDefaultPolicy() { // Create simple wrapper. KSI.Ksi ksi = GetKsi(); // Read signature, assume to be not extended IKsiSignature signature = LoadUnextendedSignature(); // We need to compute the hash from the original data, to make sure it // matches the one in the signature and has not been changed // Use the same algorithm as the input hash in the signature DataHash documentHash = KsiProvider.CreateDataHasher(signature.InputHash.Algorithm) .AddData(File.ReadAllBytes("Resources/infile.txt")) .GetHash(); // Do the verification and check the result. // At first KSI signature is verified against given document hash. // Then the signature is extended. If extending succeeds then the signature is verified // against publications file (publications file is automatically downloaded by simple wrapper). // If extending is not yet possible then key based verification is done. VerificationResult verificationResult = ksi.Verify(signature, documentHash); if (verificationResult.ResultCode == VerificationResultCode.Ok) { Console.WriteLine("VerifyUnextendedSignatureUsingDefaultPolicy > signature valid"); } else { Console.WriteLine("VerifyUnextendedSignatureUsingDefaultPolicy > verification failed with error > " + verificationResult.VerificationError); } }
public void VerifyKeyBased() { KSI.Ksi ksi = GetKsi(); // Read signature, assume to be not extended IKsiSignature signature = LoadUnextendedSignature(); DataHash documentHash = KsiProvider.CreateDataHasher(signature.InputHash.Algorithm) .AddData(File.ReadAllBytes("Resources/infile.txt")) .GetHash(); VerificationPolicy policy = new KeyBasedVerificationPolicy(new X509Store(StoreName.Root), GetCertificateSubjectRdnSelector()); VerificationContext context = new VerificationContext(signature) { DocumentHash = documentHash, PublicationsFile = ksi.GetPublicationsFile(), }; VerificationResult verificationResult = policy.Verify(context); if (verificationResult.ResultCode == VerificationResultCode.Ok) { Console.WriteLine("VerifyKeyBased > signature valid"); } else { Console.WriteLine("VerifyKeyBased > signature verification failed with error > " + verificationResult.VerificationError); } }
public void VerifyExtendedSignatureUsingPublicationsCodeAutoExtend() { // Read signature, assume to be not extended IKsiSignature signature = LoadUnextendedSignature(); DataHash documentHash = KsiProvider.CreateDataHasher(signature.InputHash.Algorithm) .AddData(File.ReadAllBytes("Resources/infile.txt")) .GetHash(); PublicationData publicationData = new PublicationData("AAAAAA-CWYEKQ-AAIYPA-UJ4GRT-HXMFBE-OTB4AB-XH3PT3-KNIKGV-PYCJXU-HL2TN4-RG6SCC-3ZGSBM"); // Do the verification and check the result VerificationPolicy policy = new PublicationBasedVerificationPolicy(); VerificationContext context = new VerificationContext(signature) { DocumentHash = documentHash, UserPublication = publicationData, IsExtendingAllowed = true, KsiService = GetKsiService(), }; VerificationResult verificationResult = policy.Verify(context); if (verificationResult.ResultCode == VerificationResultCode.Ok) { Console.WriteLine("VerifyExtendedSignatureUsingPublicationsCodeAutoExtend > signature valid"); } else { Console.WriteLine("VerifyExtendedSignatureUsingPublicationsCodeAutoExtend > signature verification failed with error > " + verificationResult.VerificationError); } }
public void VerifyExtendedSignatureUsingPublicationsCode() { // Read the existing signature, assume it is extended IKsiSignature signature = LoadExtendedSignature(); DataHash documentHash = KsiProvider.CreateDataHasher(signature.InputHash.Algorithm) .AddData(File.ReadAllBytes("Resources/infile.txt")) .GetHash(); // The trust anchor in this example is the publication code in Financial Times or on Twitter PublicationData publicationData = new PublicationData("AAAAAA-CWYEKQ-AAIYPA-UJ4GRT-HXMFBE-OTB4AB-XH3PT3-KNIKGV-PYCJXU-HL2TN4-RG6SCC-3ZGSBM"); // Do the verification and check the result VerificationPolicy policy = new PublicationBasedVerificationPolicy(); VerificationContext context = new VerificationContext(signature) { DocumentHash = documentHash, UserPublication = publicationData }; VerificationResult verificationResult = policy.Verify(context); if (verificationResult.ResultCode == VerificationResultCode.Ok) { Console.WriteLine("VerifyExtendedSignatureUsingPublicationsCode > signature valid"); } else { Console.WriteLine("VerifyExtendedSignatureUsingPublicationsCode > signature verification failed with error > " + verificationResult.VerificationError); } }
public void LinkUserIdToSignature() { BlockSigner ksiBlockSigner = new BlockSigner(GetKsiService()); IDataHasher dh = KsiProvider.CreateDataHasher(HashAlgorithm.Sha2256); // This is the data we are signing string data = "data"; dh.AddData(Encoding.UTF8.GetBytes(data)); // Suppose that this is the user that initiated the signing // and it has been verified using a 3rd party authentication provider (e.g. LDAP) string userId = "john.smith"; // Add both, the data and the user to the block signer ksiBlockSigner.Add(dh.GetHash(), new IdentityMetadata(userId)); IKsiSignature[] signatures = ksiBlockSigner.Sign().ToArray(); // We should get only one signature as we only had one item that we signed Assert.AreEqual(1, signatures.Length); // Print the last part of the identity to show john.smith is there IIdentity[] identity = signatures[0].GetIdentity().ToArray(); Console.WriteLine("User: " + identity[identity.Length - 1].ClientId); // Store the signature as needed // ... }
public void SignStaticByteArrayEmptyTest() { Ksi ksi = GetStaticKsi(Resources.KsiService_AggregationResponsePdu_SignedZeroBytes, 6607061513599596791); byte[] documentBytes = new byte[] { }; IKsiSignature signature = ksi.Sign(documentBytes); Verify(signature, KsiProvider.CreateDataHasher(HashAlgorithm.Default).AddData(documentBytes).GetHash()); }
/// <summary> /// Hash two hashes together. /// </summary> /// <param name="hashA">first hash</param> /// <param name="hashB">second hash</param> /// <param name="level">hash chain level</param> /// <returns>resulting hash</returns> private DataHash GetStepHash(byte[] hashA, byte[] hashB, ulong level) { IDataHasher hasher = KsiProvider.CreateDataHasher(_aggrAlgorithm); hasher.AddData(hashA); hasher.AddData(hashB); hasher.AddData(Util.EncodeUnsignedLong(level)); return(hasher.GetHash()); }
/// <summary> /// Hash two hashes together with algorithm. /// </summary> /// <param name="algorithm">hash algorithm</param> /// <param name="hashA">hash a</param> /// <param name="hashB">hash b</param> /// <returns>result hash</returns> private static DataHash GetStepHash(HashAlgorithm algorithm, byte[] hashA, byte[] hashB) { IDataHasher hasher = KsiProvider.CreateDataHasher(algorithm); hasher.AddData(hashA); hasher.AddData(hashB); hasher.AddData(new byte[] { 0xFF }); return(hasher.GetHash()); }
public void AsyncSignHashTest(KsiService service) { byte[] data = Encoding.UTF8.GetBytes("This is my document"); IDataHasher dataHasher = KsiProvider.CreateDataHasher(); dataHasher.AddData(data); DataHash dataHash = dataHasher.GetHash(); ManualResetEvent waitHandle = new ManualResetEvent(false); IKsiSignature signature = null; object testObject = new object(); bool isAsyncStateCorrect = false; service.BeginSign(dataHash, delegate(IAsyncResult ar) { try { isAsyncStateCorrect = ar.AsyncState == testObject; signature = service.EndSign(ar); } catch (Exception ex) { Assert.Fail("Unexpected exception: " + ex); } finally { waitHandle.Set(); } }, testObject); Assert.IsTrue(waitHandle.WaitOne(10000), "Wait handle timed out."); Assert.IsNotNull(signature, "Signature should not be null."); Assert.AreEqual(true, isAsyncStateCorrect, "Unexpected async state."); VerificationContext verificationContext = new VerificationContext(signature) { DocumentHash = dataHash }; InternalVerificationPolicy policy = new InternalVerificationPolicy(); VerificationResult verificationResult = policy.Verify(verificationContext); Assert.AreEqual(VerificationResultCode.Ok, verificationResult.ResultCode, "Signature should verify with internal policy"); }
/// <summary> /// Get output hash for RFC 3161 from document hash /// </summary> /// <returns>aggregation input hash</returns> public DataHash GetOutputHash() { IDataHasher hasher = KsiProvider.CreateDataHasher(_tstInfoAlgorithm); hasher.AddData(_tstInfoPrefix.Value); hasher.AddData(InputHash.Value); hasher.AddData(_tstInfoSuffix.Value); DataHash inputHash = hasher.GetHash(); hasher = KsiProvider.CreateDataHasher(_signedAttributesAlgorithm); hasher.AddData(_signedAttributesPrefix.Value); hasher.AddData(inputHash.Value); hasher.AddData(_signedAttributesSuffix.Value); return(hasher.GetHash()); }
/// <see cref="VerificationRule.Verify" /> public override VerificationResult Verify(IVerificationContext context) { IKsiSignature signature = GetSignature(context); if (!signature.IsRfc3161Signature) { return(new VerificationResult(GetRuleName(), VerificationResultCode.Ok)); } DataHash aggregationHashChainInputHash = GetAggregationHashChains(signature, false)[0].InputHash; DataHash inputHash = KsiProvider.CreateDataHasher(aggregationHashChainInputHash.Algorithm) .AddData(signature.Rfc3161Record.GetOutputHash().Imprint) .GetHash(); return(inputHash != aggregationHashChainInputHash ? new VerificationResult(GetRuleName(), VerificationResultCode.Fail, VerificationError.Int01) : new VerificationResult(GetRuleName(), VerificationResultCode.Ok)); }
public void SignMultipleItemsWithLocalAggregation() { BlockSigner ksiBlockSigner = new BlockSigner(GetKsiService()); int itemCount = 50; // Add the items that need to be signed to the block signer IDataHasher dh = KsiProvider.CreateDataHasher(HashAlgorithm.Sha2256); for (int i = 1; i <= itemCount; i++) { dh.Reset(); dh.AddData(Encoding.UTF8.GetBytes(i.ToString())); ksiBlockSigner.Add(dh.GetHash()); } // Submit the signing request IEnumerable <IKsiSignature> signatures = ksiBlockSigner.Sign(); // Just to illustrate that there are as many signatures as items Assert.AreEqual(itemCount, signatures.Count()); // Store the signatures as needed // ... }
public void BlockSignerGetUniSignaturesParallelTest(Ksi ksi) { ManualResetEvent waitHandle = new ManualResetEvent(false); int[] treeSizes = new[] { 1, 2, 3, 4, 5 }; int doneCount = 0; int runCount = treeSizes.Length; string errorMessage = null; Random random = new Random(); IdentityMetadata metadata = new IdentityMetadata("test client id"); foreach (int j in treeSizes) { int k = j; Task.Run(() => { Console.WriteLine("Document count: " + k); BlockSigner blockSigner = new BlockSigner(GetHttpKsiService()); List <DataHash> hashes = new List <DataHash>(); byte[] buffer = new byte[10]; for (int i = 0; i < k; i++) { IDataHasher hasher = KsiProvider.CreateDataHasher(); random.NextBytes(buffer); hasher.AddData(buffer); hashes.Add(hasher.GetHash()); } foreach (DataHash hash in hashes) { blockSigner.Add(hash, metadata); } try { int i = 0; foreach (IKsiSignature ksiSignature in blockSigner.Sign()) { Verify(ksi, ksiSignature, hashes[i++]); } } catch (Exception ex) { Console.WriteLine(DateTime.Now.ToString("HH:mm:ss.fff") + " Error " + k + ". " + ex); if (errorMessage == null) { errorMessage = ex.ToString(); } } finally { doneCount++; Console.WriteLine("Done " + k); if (doneCount == runCount) { waitHandle.Set(); } } }); } Console.WriteLine(DateTime.Now.ToString("HH:mm:ss.fff") + " Waiting ..."); Assert.IsTrue(waitHandle.WaitOne(20000), "Wait handle timed out."); if (errorMessage != null) { Assert.Fail("ERROR: " + errorMessage); } Console.WriteLine(DateTime.Now.ToString("HH:mm:ss.fff") + " All done."); }