bool ValidBundle_SingleItem(string transactionTrytes) { var tran = new TransactionItem(transactionTrytes); var bundleHash = tran.Bundle; var bundleTrytes = tran.GetBundleTrytes(); var curl = new Kerl(); String trxTrytes = transactionTrytes.Substring(2187, 162); Assert.AreEqual(bundleTrytes, trxTrytes); // Absorb bundle hash + value + timestamp + lastIndex + currentIndex trytes. curl.Absorb(Utils.Converter.ToTrits(trxTrytes)); int[] bundleFromTrxs = new int[243]; curl.Squeeze(bundleFromTrxs); String bundleFromTxString = Utils.Converter.ToTrytes(bundleFromTrxs); // Check if bundle hash is the same as returned by tx object if (!bundleFromTxString.Equals(bundleHash)) { throw new ArgumentException($"INVALID_BUNDLE_HASH_ERROR: Expected: {bundleFromTxString} but your bundle is {bundleHash}"); } // Last tx in the bundle should have currentIndex === lastIndex //bundle.setLength(bundle.getTransactions().size()); return(tran.CurrentIndex == tran.LastIndex); }
public static void FinalizeBundleHash(this IEnumerable <TransactionItem> transactionItems) { var validBundle = false; while (!validBundle) { var kerl = new Kerl(); kerl.Reset(); var transactionCount = transactionItems.Count(); for (int i = 0; i < transactionCount; i++) { var transaction = transactionItems.ElementAt(i); var valueTrits = Converter.GetTrits(transaction.Value).ToLength(81); var timestampTrits = Converter.GetTrits(transaction.Timestamp).ToLength(27); var currentIndexTrits = Converter.GetTrits(transaction.CurrentIndex = ("" + i)).ToLength(27); var lastIndexTrits = Converter.GetTrits( transaction.LastIndex = ("" + (transactionCount - 1))).ToLength(27); string stringToConvert = transaction.Address + Converter.GetTrytes(valueTrits) + transaction.Tag + Converter.GetTrytes(timestampTrits) + Converter.GetTrytes(currentIndexTrits) + Converter.GetTrytes(lastIndexTrits); var t = Converter.GetTrits(stringToConvert); kerl.Absorb(t, 0, t.Length); } sbyte[] hash = new sbyte[Curl.HASH_LENGTH]; kerl.Squeeze(hash, 0, hash.Length); string hashInTrytes = Converter.GetTrytes(hash); foreach (var transaction in transactionItems) { transaction.Bundle = hashInTrytes; } var normalizedHash = NormalizedBundle(hashInTrytes); if (normalizedHash.Contains(13)) { // Insecure bundle. Increment Tag and recompute bundle hash. var firstTransaction = transactionItems.ElementAt(0); var increasedTag = Adder.Add(Converter.GetTrits(firstTransaction.Tag), new sbyte[1]); firstTransaction.Tag = Converter.GetTrytes(increasedTag); } else { validBundle = true; } } }
public void kurlMultiAbsorbMultiSqueeze() { int[] initial_value = Converter.ToTrits("G9JYBOMPUXHYHKSNRNMMSSZCSHOFYOYNZRSZMAAYWDYEIMVVOGKPJBVBM9TDPULSFUNMTVXRKFIDOHUXXVYDLFSZYZTWQYTE9SPYYWYTXJYQ9IFGYOLZXWZBKWZN9QOOTBQMWMUBLEWUEEASRHRTNIQWJQNDWRYLCA"); ICurl k = new Kerl(); k.Absorb(initial_value, 0, initial_value.Length); int[] hash_value = new int[Curl.HashLength * 2]; k.Squeeze(hash_value, 0, hash_value.Length); String hash = Converter.ToTrytes(hash_value); Assert.AreEqual("LUCKQVACOGBFYSPPVSSOXJEKNSQQRQKPZC9NXFSMQNRQCGGUL9OHVVKBDSKEQEBKXRNUJSRXYVHJTXBPDWQGNSCDCBAIRHAQCOWZEBSNHIJIGPZQITIBJQ9LNTDIBTCQ9EUWKHFLGFUVGGUWJONK9GBCDUIMAYMMQX", hash); }
public void kurlOneAbsorb() { int[] initial_value = Converter.ToTrits("EMIDYNHBWMBCXVDEFOFWINXTERALUKYYPPHKP9JJFGJEIUY9MUDVNFZHMMWZUYUSWAIOWEVTHNWMHANBH"); ICurl k = new Kerl(); k.Absorb(initial_value, 0, initial_value.Length); int[] hash_value = new int[Curl.HashLength]; k.Squeeze(hash_value, 0, hash_value.Length); String hash = Converter.ToTrytes(hash_value); Assert.AreEqual("EJEAOOZYSAWFPZQESYDHZCGYNSTWXUMVJOVDWUNZJXDGWCLUFGIMZRMGCAZGKNPLBRLGUNYWKLJTYEAQX", hash); }
public void TestGenerateTrytesAndMultiSqueeze() { var path = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location); var isNetStandard = path.Contains("Standard"); var netStandardExtension = isNetStandard ? "../" : ""; // CSV from Python lib. Thanks alot! using (var reader = new StreamReader(@"../" + netStandardExtension + "../Cryptography/generate_trytes_and_multi_squeeze.csv")) { var i = 0; while (!reader.EndOfStream) { var line = reader.ReadLine(); if (line == null || i == 0) { i++; continue; } var values = line.Split(','); var trytes = values[0]; var hashes1 = values[1]; var hashes2 = values[2]; var hashes3 = values[3]; var trits = Converter.TrytesToTrits(trytes); var kerl = new Kerl(); kerl.Absorb(trits); var tritsOut = new int[Constants.TritHashLength]; kerl.Squeeze(tritsOut); var trytesOut = Converter.TritsToTrytes(tritsOut); Assert.AreEqual(hashes1, trytesOut); tritsOut = new int[Constants.TritHashLength]; kerl.Squeeze(tritsOut); trytesOut = Converter.TritsToTrytes(tritsOut); Assert.AreEqual(hashes2, trytesOut); tritsOut = new int[Constants.TritHashLength]; kerl.Squeeze(tritsOut); trytesOut = Converter.TritsToTrytes(tritsOut); Assert.AreEqual(hashes3, trytesOut); i++; } } }
public void kurlMultiSqueeze() { int[] initial_value = Converter.ToTrits("9MIDYNHBWMBCXVDEFOFWINXTERALUKYYPPHKP9JJFGJEIUY9MUDVNFZHMMWZUYUSWAIOWEVTHNWMHANBH"); ICurl k = new Kerl(); k.Absorb(initial_value, 0, initial_value.Length); int[] hash_value = new int[Curl.HashLength * 2]; k.Squeeze(hash_value, 0, hash_value.Length); String hash = Converter.ToTrytes(hash_value); Assert.AreEqual("G9JYBOMPUXHYHKSNRNMMSSZCSHOFYOYNZRSZMAAYWDYEIMVVOGKPJBVBM9TDPULSFUNMTVXRKFIDOHUXXVYDLFSZYZTWQYTE9SPYYWYTXJYQ9IFGYOLZXWZBKWZN9QOOTBQMWMUBLEWUEEASRHRTNIQWJQNDWRYLCA", hash); }
private static string CalculateChecksum(string address) { // TODO inject curl ICurl curl = new Kerl(); curl.Reset(); curl.Absorb(Converter.ToTrits(address)); var checksumTrits = new int[Sponge.HashLength]; curl.Squeeze(checksumTrits); var checksum = Converter.ToTrytes(checksumTrits); return(checksum.Substring(72, 9)); }
public void ShouldCreateValidHash1() { var trits = Converter.ToTrits( "GYOMKVTSNHVJNCNFBBAH9AAMXLPLLLROQY99QN9DLSJUHDPBLCFFAIQXZA9BKMBJCYSFHFPXAHDWZFEIZ"); var kerl = new Kerl(); kerl.Reset(); kerl.Absorb(trits, 0, trits.Length); var hashTrits = new int[trits.Length]; kerl.Squeeze(hashTrits, 0, 243); var hash = Converter.ToTrytes(hashTrits); Assert.AreEqual(hash, "OXJCNFHUNAHWDLKKPELTBFUCVW9KLXKOGWERKTJXQMXTKFKNWNNXYD9DMJJABSEIONOSJTTEVKVDQEWTW"); }
public void TestGenerateTrytesAndMultiSqueeze() { // CSV from Python lib. Thanks alot! using (var reader = new StreamReader(@"../../Tests/Cryptography/generate_trytes_and_multi_squeeze.csv")) { var i = 0; while (!reader.EndOfStream) { var line = reader.ReadLine(); if (line == null || i == 0) { i++; continue; } var values = line.Split(','); var trytes = values[0]; var hashes1 = values[1]; var hashes2 = values[2]; var hashes3 = values[3]; var trits = Converter.TrytesToTrits(trytes); var kerl = new Kerl(); kerl.Absorb(trits); var tritsOut = new int[Kerl.HashLength]; kerl.Squeeze(tritsOut); var trytesOut = Converter.TritsToTrytes(tritsOut); Assert.AreEqual(hashes1, trytesOut); tritsOut = new int[Kerl.HashLength]; kerl.Squeeze(tritsOut); trytesOut = Converter.TritsToTrytes(tritsOut); Assert.AreEqual(hashes2, trytesOut); tritsOut = new int[Kerl.HashLength]; kerl.Squeeze(tritsOut); trytesOut = Converter.TritsToTrytes(tritsOut); Assert.AreEqual(hashes3, trytesOut); i++; } } }
public void KerlOneAbsorbMethod2() { var input = "EMIDYNHBWMBCXVDEFOFWINXTERALUKYYPPHKP9JJFGJEIUY9MUDVNFZHMMWZUYUSWAIOWEVTHNWMHANBH"; var expected = "EJEAOOZYSAWFPZQESYDHZCGYNSTWXUMVJOVDWUNZJXDGWCLUFGIMZRMGCAZGKNPLBRLGUNYWKLJTYEAQX"; var trits = Converter.GetTrits(input); var kerl = new Kerl(); kerl.Absorb(trits, 0, trits.Length); var hashTrits = new sbyte[Kerl.HASH_LENGTH]; kerl.Squeeze(hashTrits, 0, Kerl.HASH_LENGTH); var hash = Converter.GetTrytes(hashTrits); Assert.AreEqual(expected, hash); }
public void TestKerlOneAbsorb() { var tritValue = Converter.TrytesToTrits("KFNNRVYTYYYNHJLBTXOEFYBZTHGXHTX9XKXB9KUZDHGLKBQGPQCNHPGDSGYKWGHVXVLHPOEAWREBIVK99"); var kerl = new Kerl(); kerl.Absorb(tritValue); var hashValue = new int[Kerl.HashLength]; kerl.Squeeze(hashValue); var hash = Converter.TritsToTrytes(hashValue); Assert.AreEqual("SHTKPLZWIXLDVHAEAGFSVWNDGVIX9SDVGEHAFGXEIMLWSHDTQYNZZKPBGMUF9GNEWIGIFYWWMSCLJ9RCD", hash); }
public void KurlMultiSqueeze() { var tritValue = Converter.TrytesToTrits("9MIDYNHBWMBCXVDEFOFWINXTERALUKYYPPHKP9JJFGJEIUY9MUDVNFZHMMWZUYUSWAIOWEVTHNWMHANBH"); var kerl = new Kerl(); kerl.Absorb(tritValue); var hashValue = new int[Constants.TritHashLength * 2]; kerl.Squeeze(hashValue); var hash = Converter.TritsToTrytes(hashValue); Assert.AreEqual("G9JYBOMPUXHYHKSNRNMMSSZCSHOFYOYNZRSZMAAYWDYEIMVVOGKPJBVBM9TDPULSFUNMTVXRKFIDOHUXXVYDLFSZYZTWQYTE9SPYYWYTXJYQ9IFGYOLZXWZBKWZN9QOOTBQMWMUBLEWUEEASRHRTNIQWJQNDWRYLCA", hash); }
public void KerlMultiAbsorbMultiSqueeze() { var input = "G9JYBOMPUXHYHKSNRNMMSSZCSHOFYOYNZRSZMAAYWDYEIMVVOGKPJBVBM9TDPULSFUNMTVXRKFIDOHUXXVYDLFSZYZTWQYTE9SPYYWYTXJYQ9IFGYOLZXWZBKWZN9QOOTBQMWMUBLEWUEEASRHRTNIQWJQNDWRYLCA"; var expected = "LUCKQVACOGBFYSPPVSSOXJEKNSQQRQKPZC9NXFSMQNRQCGGUL9OHVVKBDSKEQEBKXRNUJSRXYVHJTXBPDWQGNSCDCBAIRHAQCOWZEBSNHIJIGPZQITIBJQ9LNTDIBTCQ9EUWKHFLGFUVGGUWJONK9GBCDUIMAYMMQX"; var trits = Converter.GetTrits(input); var kerl = new Kerl(); kerl.Initialize(); kerl.Absorb(trits, 0, trits.Length); var hashTrits = new sbyte[Kerl.HASH_LENGTH * 2]; kerl.Squeeze(hashTrits, 0, Kerl.HASH_LENGTH * 2); var hash = Converter.GetTrytes(hashTrits); Assert.AreEqual(expected, hash); }
public void KerlAbsorbMultiSqueeze() { var input = "9MIDYNHBWMBCXVDEFOFWINXTERALUKYYPPHKP9JJFGJEIUY9MUDVNFZHMMWZUYUSWAIOWEVTHNWMHANBH"; var expected = "G9JYBOMPUXHYHKSNRNMMSSZCSHOFYOYNZRSZMAAYWDYEIMVVOGKPJBVBM9TDPULSFUNMTVXRKFIDOHUXXVYDLFSZYZTWQYTE9SPYYWYTXJYQ9IFGYOLZXWZBKWZN9QOOTBQMWMUBLEWUEEASRHRTNIQWJQNDWRYLCA"; var trits = Converter.GetTrits(input); var kerl = new Kerl(); kerl.Initialize(); kerl.Absorb(trits, 0, trits.Length); var hashTrits = new sbyte[Kerl.HASH_LENGTH * 2]; kerl.Squeeze(hashTrits, 0, Kerl.HASH_LENGTH * 2); var hash = Converter.GetTrytes(hashTrits); Assert.AreEqual(expected, hash); }
/// <summary> /// The finalize. /// </summary> public void Finalize() { if (this.Hash != null) { throw new InvalidOperationException("BundleHash is already finalized!"); } if (this.Transactions.Count == 0) { throw new ArgumentException("At least one transaction must be added before finalizing bundle."); } var balance = this.Balance; if (balance < 0) { if (this.RemainderAddress != null && !string.IsNullOrEmpty(this.RemainderAddress.Value)) { this.Transactions.Add(new Transaction { Address = this.RemainderAddress, Tag = Tag.Empty, Value = -balance, ObsoleteTag = Tag.Empty }); } else { throw new InvalidOperationException("BundleHash balance is not even. Add remainder address."); } } if (balance > 0) { throw new InvalidOperationException("Insufficient value submitted."); } string bundleHashTrytes; var valid = false; var kerl = new Kerl(); do { kerl.Reset(); for (var i = 0; i < this.Transactions.Count; i++) { this.Transactions[i].CurrentIndex = i; this.Transactions[i].LastIndex = this.Transactions.Count - 1; var transactionTrits = Converter.TrytesToTrits(this.Transactions[i].ToTrytes()); kerl.Absorb(transactionTrits); } var hash = new int[Kerl.HashLength]; kerl.Squeeze(hash); bundleHashTrytes = Converter.TritsToTrytes(hash); var normalizedBundleValue = NormalizeBundle(bundleHashTrytes); if (Array.IndexOf(normalizedBundleValue, 13) != -1) { var obsoleteTagTrits = Converter.TrytesToTrits(this.Transactions[0].ObsoleteTag.Value); Converter.Increment(obsoleteTagTrits, 81); this.Transactions[0].ObsoleteTag = new Tag(Converter.TritsToTrytes(obsoleteTagTrits)); } else { valid = true; } }while (!valid); this.Hash = new Hash(bundleHashTrytes); foreach (var transaction in this.Transactions) { transaction.BundleHash = this.Hash; } }