From d1702c81f5b3deab5a1284cb8e3bd7a86650f4e1 Mon Sep 17 00:00:00 2001 From: Sergio Flores Date: Sat, 9 Oct 2021 22:15:14 +0100 Subject: [PATCH 01/10] Validate file name case in "wallet deploy" command --- Spook/Modules/WalletModule.cs | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/Spook/Modules/WalletModule.cs b/Spook/Modules/WalletModule.cs index 55fc3cd..3c89eba 100644 --- a/Spook/Modules/WalletModule.cs +++ b/Spook/Modules/WalletModule.cs @@ -617,6 +617,14 @@ private static VMObject ExecuteScript(byte[] script, ContractInterface abi, stri throw new Exception("Script execution failed for: " + methodName); } + private static bool FileExistsCaseSensitive(string filename) + { + string name = Path.GetDirectoryName(filename); + + return name != null + && Array.Exists(Directory.GetFiles(name), s => s == Path.GetFullPath(filename)); + } + private static void DeployOrUpgrade(string[] args, SpookSettings settings, NexusAPI api, BigInteger minFee, bool isUpgrade) { if (args.Length != 1) @@ -633,6 +641,11 @@ private static void DeployOrUpgrade(string[] args, SpookSettings settings, Nexus throw new CommandException("Provided file does not exist"); } + if (!FileExistsCaseSensitive(fileName)) + { + throw new CommandException("Provided file case does not match real file name case"); + } + var extension = ScriptModule.ScriptExtension; if (!fileName.EndsWith(extension)) @@ -680,6 +693,7 @@ private static void DeployOrUpgrade(string[] args, SpookSettings settings, Nexus throw new CommandException("Failed to obtain nexus version via API"); } + bool isToken = ValidationUtils.IsValidTicker(contractName); var availableFlags = Enum.GetValues(typeof(TokenFlags)).Cast().ToArray(); From d6b93a5c9d2005818775e5ad8134d3dd0d1da48a Mon Sep 17 00:00:00 2001 From: alexmpa <62516783+alexmpa@users.noreply.github.com> Date: Fri, 13 Aug 2021 23:39:42 +0300 Subject: [PATCH 02/10] Fix Eth swapper crashing on tx-es because of 'Header byte out of range' exception --- Spook/Chains/Ethereum/EvmBlockCrawler.cs | 25 ++++++++++++++++- Spook/Interop/EthereumInterop.cs | 34 +++++++++++++++++++++--- 2 files changed, 54 insertions(+), 5 deletions(-) diff --git a/Spook/Chains/Ethereum/EvmBlockCrawler.cs b/Spook/Chains/Ethereum/EvmBlockCrawler.cs index 52ffcf9..6f507ad 100644 --- a/Spook/Chains/Ethereum/EvmBlockCrawler.cs +++ b/Spook/Chains/Ethereum/EvmBlockCrawler.cs @@ -21,6 +21,9 @@ using InteropTransfers = System.Collections.Generic.Dictionary>>; +using System.Linq; +using System; + namespace Phantasma.Spook.Chains { public class CrawledBlock @@ -103,7 +106,27 @@ public InteropTransfers ExtractInteropTransfers(Blockchain.Nexus nexus, Logger l var txr = txVo.TransactionReceipt; var tx = txVo.Transaction; - var interopAddress = addressExtractor(tx); + Address interopAddress; + try + { + interopAddress = EthereumInterop.ExtractInteropAddress(tx, logger); + } + catch(Exception e) + { + if (e.ToString().Contains("Header byte out of range")) + { + // Ignoring this exception and skipping this tx. + // RecoverFromSignature() crashed and we cannot avoid it atm. + // Related to EIP-1559, example of probematic tx: https://etherscan.io/tx/0xb022c146d8d1e684de0c1faae43e7ce36afb6969719adfdcafcc5bb7d5913185 + // TODO Fix by updating to new Nethereum and dealing with EIP-1559 better. + logger.Message("Warning: Skipping 'Header byte out of range' tx: " + tx.TransactionHash); + continue; + } + else + { + throw; + } + } var transferEvents = txr.DecodeAllEvents(); //var swapEvents = txr.DecodeAllEvents(); var nodeSwapAddresses = swapAddresses.Select(x => encodeHandler(x)).ToList(); diff --git a/Spook/Interop/EthereumInterop.cs b/Spook/Interop/EthereumInterop.cs index 5bce041..89fc4f4 100644 --- a/Spook/Interop/EthereumInterop.cs +++ b/Spook/Interop/EthereumInterop.cs @@ -327,14 +327,20 @@ public static Tuple MakeInteropBlock(Logger return null; } - public static Address ExtractInteropAddress(Nethereum.RPC.Eth.DTOs.Transaction tx) + public static Address ExtractInteropAddress(Nethereum.RPC.Eth.DTOs.Transaction tx, Logger logger) { //Using the transanction from RPC to build a txn for signing / signed var transaction = Nethereum.Signer.TransactionFactory.CreateTransaction(tx.To, tx.Gas, tx.GasPrice, tx.Value, tx.Input, tx.Nonce, tx.R, tx.S, tx.V); - - //Get the account sender recovered + + //Get the account sender recovered Nethereum.Signer.EthECKey accountSenderRecovered = null; + // TODO To be used with Nethereum 4: + // 1) CreateLegacyTransaction()/LegacyTransactionChainId + // or + // 2) var signature = new Nethereum.Signer.EthECDSASignature(new Org.BouncyCastle.Math.BigInteger(tx.R.Replace("0x", ""), 16), new Org.BouncyCastle.Math.BigInteger(tx.S.Replace("0x", ""), 16), new Org.BouncyCastle.Math.BigInteger(tx.V.Replace("0x", ""), 16).ToByteArray()); + // accountSenderRecovered = Nethereum.Signer.EthECKey.RecoverFromSignature(signature, System.Text.Encoding.UTF8.GetBytes(tx.TransactionHash.Replace("0x", ""))); + if (transaction is Nethereum.Signer.TransactionChainId) { var txnChainId = transaction as Nethereum.Signer.TransactionChainId; @@ -455,7 +461,27 @@ private static Dictionary> GetInteropTransfers(Nex } var nodeSwapAddresses = swapAddresses.Select(x => EthereumWallet.EncodeAddress(x)); - var interopAddress = ExtractInteropAddress(tx); + Address interopAddress; + try + { + interopAddress = ExtractInteropAddress(tx, logger); + } + catch(Exception e) + { + if(e.ToString().Contains("Header byte out of range")) + { + // Ignoring this exception and skipping this tx. + // RecoverFromSignature() crashed and we cannot avoid it atm. + // Related to EIP-1559, example of probematic tx: https://etherscan.io/tx/0xb022c146d8d1e684de0c1faae43e7ce36afb6969719adfdcafcc5bb7d5913185 + // TODO Fix by updating to new Nethereum and dealing with EIP-1559 better. + logger.Message("Warning: Skipping 'Header byte out of range' tx: " + tx.TransactionHash); + return interopTransfers; + } + else + { + throw; + } + } // ERC721 (NFT) // TODO currently this code block is mostly copypaste from ERC20 block, later make a single method for both... From b9250bd57ba30ff6b34d5f4eda94dda591fb32a3 Mon Sep 17 00:00:00 2001 From: Merl111 Date: Thu, 30 Sep 2021 09:59:25 +0200 Subject: [PATCH 03/10] cleanup, change log level --- Spook/Interop/EthereumInterop.cs | 34 +++++++++++++------------- StorageAnalyser/Analyser.cs | 3 +-- StorageAnalyser/StorageAnalyser.csproj | 3 +++ 3 files changed, 21 insertions(+), 19 deletions(-) diff --git a/Spook/Interop/EthereumInterop.cs b/Spook/Interop/EthereumInterop.cs index 89fc4f4..47231ce 100644 --- a/Spook/Interop/EthereumInterop.cs +++ b/Spook/Interop/EthereumInterop.cs @@ -462,25 +462,25 @@ private static Dictionary> GetInteropTransfers(Nex var nodeSwapAddresses = swapAddresses.Select(x => EthereumWallet.EncodeAddress(x)); Address interopAddress; - try - { - interopAddress = ExtractInteropAddress(tx, logger); + try + { + interopAddress = ExtractInteropAddress(tx, logger); } catch(Exception e) - { - if(e.ToString().Contains("Header byte out of range")) - { - // Ignoring this exception and skipping this tx. - // RecoverFromSignature() crashed and we cannot avoid it atm. - // Related to EIP-1559, example of probematic tx: https://etherscan.io/tx/0xb022c146d8d1e684de0c1faae43e7ce36afb6969719adfdcafcc5bb7d5913185 - // TODO Fix by updating to new Nethereum and dealing with EIP-1559 better. - logger.Message("Warning: Skipping 'Header byte out of range' tx: " + tx.TransactionHash); - return interopTransfers; - } - else - { - throw; - } + { + if(e.ToString().Contains("Header byte out of range")) + { + // Ignoring this exception and skipping this tx. + // RecoverFromSignature() crashed and we cannot avoid it atm. + // Related to EIP-1559, example of probematic tx: https://etherscan.io/tx/0xb022c146d8d1e684de0c1faae43e7ce36afb6969719adfdcafcc5bb7d5913185 + // TODO Fix by updating to new Nethereum and dealing with EIP-1559 better. + logger.Debug("Warning: Skipping 'Header byte out of range' tx: " + tx.TransactionHash); + return interopTransfers; + } + else + { + throw; + } } // ERC721 (NFT) diff --git a/StorageAnalyser/Analyser.cs b/StorageAnalyser/Analyser.cs index 32fcfa9..dfd5ee7 100644 --- a/StorageAnalyser/Analyser.cs +++ b/StorageAnalyser/Analyser.cs @@ -184,7 +184,7 @@ private void DumpBalances(Chain chain, IToken token) var fungible = token.IsFungible(); - var prefix = fungible ? BalanceSheet.MakePrefix(symbol) : OwnershipSheet.MakePrefix(symbol); + var prefix = fungible ? BalanceSheet.MakePrefix(symbol) : System.Text.Encoding.UTF8.GetBytes($".ids.{symbol}"); var store = chain.Storage; @@ -456,7 +456,6 @@ private void DumpBlocks(Chain chain) BigInteger balance = balances.ContainsKey(key) ? balances[key] : 0; var chainBalance = chain.GetTokenBalance(chain.Storage, data.Symbol, Address.FromText(addr)); - Console.WriteLine(chainBalance); transferList.Add(new TransferEntry(block.Height, tx.Hash.ToString(), block.Timestamp.Value, evt.Kind, addr, data.Symbol, amount.ToString(), balance.ToString(), chainBalance.ToString())); diff --git a/StorageAnalyser/StorageAnalyser.csproj b/StorageAnalyser/StorageAnalyser.csproj index 1c418f3..5664943 100644 --- a/StorageAnalyser/StorageAnalyser.csproj +++ b/StorageAnalyser/StorageAnalyser.csproj @@ -11,4 +11,7 @@ + + + From 7d94c8f51ce8d9876f7b6e173985f69eaf393db4 Mon Sep 17 00:00:00 2001 From: Merl111 Date: Thu, 30 Sep 2021 14:20:35 +0200 Subject: [PATCH 04/10] push version --- Spook/Spook.Node.csproj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Spook/Spook.Node.csproj b/Spook/Spook.Node.csproj index fe30223..f38c083 100644 --- a/Spook/Spook.Node.csproj +++ b/Spook/Spook.Node.csproj @@ -2,7 +2,7 @@ 2018 - 2021 Phantasma.io Phantasma.Spook.CLI - 1.5.1 + 1.6 The Phantasma Team netcoreapp3.1 spook-cli From b52e82f40d3958d11edb99c57af2d599eff9bc9c Mon Sep 17 00:00:00 2001 From: Merl111 Date: Thu, 30 Sep 2021 14:20:48 +0200 Subject: [PATCH 05/10] add bsc to address creation --- Spook/Command/CommandDispatcher.Oracle.cs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/Spook/Command/CommandDispatcher.Oracle.cs b/Spook/Command/CommandDispatcher.Oracle.cs index 08a9c36..b00324e 100644 --- a/Spook/Command/CommandDispatcher.Oracle.cs +++ b/Spook/Command/CommandDispatcher.Oracle.cs @@ -254,6 +254,10 @@ protected void OnPlatformAddressAdd(string[] args) localAddress = EthereumWallet.EncodeAddress(externalAddress); break; + case BSCWallet.BSCPlatform: + localAddress = BSCWallet.EncodeAddress(externalAddress); + break; + default: throw new Exception("Unknown platform: " + platform); } From 13d212d36444fd655c4f622bddde53a3155fdc4a Mon Sep 17 00:00:00 2001 From: Merl111 Date: Tue, 12 Oct 2021 12:20:14 +0200 Subject: [PATCH 06/10] cleanup logging --- Spook/Chains/Ethereum/EvmBlockCrawler.cs | 33 ++++++++++++------------ Spook/Interop/BSCInterop.cs | 2 +- Spook/Interop/EthereumInterop.cs | 2 -- Spook/Interop/TokenSwapper.cs | 4 +-- Spook/Spook.Node.csproj | 2 +- 5 files changed, 20 insertions(+), 23 deletions(-) diff --git a/Spook/Chains/Ethereum/EvmBlockCrawler.cs b/Spook/Chains/Ethereum/EvmBlockCrawler.cs index 6f507ad..ef6e7ee 100644 --- a/Spook/Chains/Ethereum/EvmBlockCrawler.cs +++ b/Spook/Chains/Ethereum/EvmBlockCrawler.cs @@ -21,9 +21,6 @@ using InteropTransfers = System.Collections.Generic.Dictionary>>; -using System.Linq; -using System; - namespace Phantasma.Spook.Chains { public class CrawledBlock @@ -119,7 +116,7 @@ public InteropTransfers ExtractInteropTransfers(Blockchain.Nexus nexus, Logger l // RecoverFromSignature() crashed and we cannot avoid it atm. // Related to EIP-1559, example of probematic tx: https://etherscan.io/tx/0xb022c146d8d1e684de0c1faae43e7ce36afb6969719adfdcafcc5bb7d5913185 // TODO Fix by updating to new Nethereum and dealing with EIP-1559 better. - logger.Message("Warning: Skipping 'Header byte out of range' tx: " + tx.TransactionHash); + logger.Debug("Warning: Skipping 'Header byte out of range' tx: " + tx.TransactionHash); continue; } else @@ -155,12 +152,12 @@ public InteropTransfers ExtractInteropTransfers(Blockchain.Nexus nexus, Logger l continue; } - logger.Message($"Found ERC20 swap: {blockId} hash: {hash} to: {evt.Event.To} from: {evt.Event.From} value: {evt.Event.Value}"); var asset = EthUtils.FindSymbolFromAsset(this.platform, nexus, evt.Log.Address); - logger.Message("asset: " + asset); + logger.Debug($@"Found {this.platform} swap: {blockId} hash: {hash} to: {evt.Event.To} + from: {evt.Event.From} value: {evt.Event.Value} asset: {asset}"); if (asset == null) { - logger.Message($"Asset [{evt.Log.Address}] not supported"); + logger.Debug($"Asset [{evt.Log.Address}] not supported"); continue; } @@ -169,9 +166,9 @@ public InteropTransfers ExtractInteropTransfers(Blockchain.Nexus nexus, Logger l var amount = PBigInteger.Parse(evt.Event.Value.ToString()); //logger.Message("nodeSwapAddress: " + nodeSwapAddress); - logger.Message("sourceAddress: " + sourceAddress); - logger.Message("targetAddress: " + targetAddress); - logger.Message("amount: " + amount); + //logger.Message("sourceAddress: " + sourceAddress); + //logger.Message("targetAddress: " + targetAddress); + //logger.Message("amount: " + amount); if (!interopTransfers[block.BlockHash].ContainsKey(evt.Log.TransactionHash)) { @@ -196,12 +193,12 @@ public InteropTransfers ExtractInteropTransfers(Blockchain.Nexus nexus, Logger l if (tx.Value != null && tx.Value.Value > 0) { - logger.Message("ETH:"); - logger.Message(block.Number.ToString()); - logger.Message(tx.TransactionHash); - logger.Message(tx.To); - logger.Message(tx.From); - logger.Message(tx.Value.ToString()); + //logger.Message("ETH:"); + //logger.Message(block.Number.ToString()); + //logger.Message(tx.TransactionHash); + //logger.Message(tx.To); + //logger.Message(tx.From); + //logger.Message(tx.Value.ToString()); var targetAddress = encodeHandler(tx.To); Console.WriteLine("target eth: " + targetAddress); @@ -219,6 +216,8 @@ public InteropTransfers ExtractInteropTransfers(Blockchain.Nexus nexus, Logger l var sourceAddress = encodeHandler(tx.From); var amount = PBigInteger.Parse(tx.Value.ToString()); + var nativeSymbol = (this.platform == "ethereum") ? "ETH" : "BNB"; + interopTransfers[block.BlockHash][tx.TransactionHash].Add ( new InteropTransfer @@ -228,7 +227,7 @@ public InteropTransfers ExtractInteropTransfers(Blockchain.Nexus nexus, Logger l DomainSettings.PlatformName, targetAddress, interopAddress, // interop address - "BNB", // TODO use const + nativeSymbol, amount ) ); diff --git a/Spook/Interop/BSCInterop.cs b/Spook/Interop/BSCInterop.cs index 14b1e48..d5aa6cc 100644 --- a/Spook/Interop/BSCInterop.cs +++ b/Spook/Interop/BSCInterop.cs @@ -382,7 +382,7 @@ public static Tuple MakeInteropBlock(Nexus n try { // TODO pass from outside to not instantiate for each call to MakeInteropBlock - Func addressEncoder = (address) => { Console.WriteLine("BSC ENCODER!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!1"); return BSCWallet.EncodeAddress(address); }; + Func addressEncoder = (address) => { return BSCWallet.EncodeAddress(address); }; Func addressExtractor = (tx) => { return BSCInterop.ExtractInteropAddress(tx); }; var crawler = new EvmBlockCrawler(logger, combinedAddresses.ToArray(), confirmations, api, diff --git a/Spook/Interop/EthereumInterop.cs b/Spook/Interop/EthereumInterop.cs index 47231ce..fda0668 100644 --- a/Spook/Interop/EthereumInterop.cs +++ b/Spook/Interop/EthereumInterop.cs @@ -354,14 +354,12 @@ public static Address ExtractInteropAddress(Nethereum.RPC.Eth.DTOs.Transaction t var point = Cryptography.ECC.ECPoint.DecodePoint(pubKey, Cryptography.ECC.ECCurve.Secp256k1); pubKey = point.EncodePoint(true); - Console.WriteLine("account recovered: " + accountSenderRecovered.GetPublicAddress()); var bytes = new byte[34]; bytes[0] = (byte)AddressKind.User; ByteArrayUtils.CopyBytes(pubKey, 0, bytes, 1, 33); var address = Address.FromBytes(bytes); - Console.WriteLine("account recovered: " + accountSenderRecovered.GetPublicAddress()); return address; } diff --git a/Spook/Interop/TokenSwapper.cs b/Spook/Interop/TokenSwapper.cs index 76655e2..7f98698 100644 --- a/Spook/Interop/TokenSwapper.cs +++ b/Spook/Interop/TokenSwapper.cs @@ -424,11 +424,11 @@ private void ProcessCompletedTasks() if (_pendingSwaps.ContainsKey(swap.hash)) { - Logger.Message($"Already known swap, ignore {swap.platform} swap: {swap.source} => {swap.destination}"); + Logger.Debug($"Already known swap, ignore {swap.platform} swap: {swap.source} => {swap.destination}"); continue; } - Logger.Message($"Detected {swap.platform} swap: {swap.source} => {swap.destination} hash: {swap.hash}"); + Logger.Debug($"Detected {swap.platform} swap: {swap.source} => {swap.destination} hash: {swap.hash}"); _pendingSwaps[swap.hash] = swap; MapSwap(swap.source, swap.hash); MapSwap(swap.destination, swap.hash); diff --git a/Spook/Spook.Node.csproj b/Spook/Spook.Node.csproj index f38c083..baf6660 100644 --- a/Spook/Spook.Node.csproj +++ b/Spook/Spook.Node.csproj @@ -2,7 +2,7 @@ 2018 - 2021 Phantasma.io Phantasma.Spook.CLI - 1.6 + 1.6.1 The Phantasma Team netcoreapp3.1 spook-cli From b6dcb14b1f7743252fa0c6c305c0338e4b4f7e7d Mon Sep 17 00:00:00 2001 From: Merl111 Date: Tue, 12 Oct 2021 12:29:19 +0200 Subject: [PATCH 07/10] fix build --- Spook/Interop/EthereumInterop.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Spook/Interop/EthereumInterop.cs b/Spook/Interop/EthereumInterop.cs index fda0668..171cf5b 100644 --- a/Spook/Interop/EthereumInterop.cs +++ b/Spook/Interop/EthereumInterop.cs @@ -377,7 +377,7 @@ public static Tuple MakeInteropBlock(Nexus n try { Func addressEncoder = (address) => { return EthereumWallet.EncodeAddress(address); }; - Func addressExtractor = (tx) => { return EthereumInterop.ExtractInteropAddress(tx); }; + Func addressExtractor = (tx) => { return EthereumInterop.ExtractInteropAddress(tx, logger); }; var crawler = new EvmBlockCrawler(logger, combinedAddresses.ToArray(), confirmations, api, addressEncoder, addressExtractor, EthereumWallet.EthereumPlatform); From ddbde12f1ad8f1223de6a2d43971dbb09a737b11 Mon Sep 17 00:00:00 2001 From: Sergio Flores Date: Tue, 12 Oct 2021 13:35:23 +0100 Subject: [PATCH 08/10] Expose node ports in API --- Spook/Spook.cs | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/Spook/Spook.cs b/Spook/Spook.cs index 94c7151..5695518 100644 --- a/Spook/Spook.cs +++ b/Spook/Spook.cs @@ -70,6 +70,8 @@ public class Spook : Runnable private string _cryptoCompareAPIKey = null; private Thread _tokenSwapperThread; + private List _availablePorts = new List(); + public NexusAPI NexusAPI { get { return _nexusApi; } } public Nexus Nexus { get { return _nexus; } } public NeoAPI NeoAPI { get { return _neoAPI; } } @@ -128,6 +130,21 @@ protected override void OnStart() _mempool = SetupMempool(); } + if (Settings.Node.Mode != NodeMode.Proxy) + { + _availablePorts.Add(new PeerPort("sync", Settings.Node.NodePort)); + } + + if (Settings.Node.HasRpc) + { + _availablePorts.Add(new PeerPort("rpc", Settings.Node.RpcPort)); + } + + if (Settings.Node.HasRest) + { + _availablePorts.Add(new PeerPort("rest", Settings.Node.RestPort)); + } + _peerCaps = SetupPeerCaps(); _node = SetupNode(); @@ -319,7 +336,7 @@ private Node SetupNode() , _mempool , _nodeKeys , Settings.Node.NodeHost - , Settings.Node.NodePort + , _availablePorts , _peerCaps , Settings.Node.Seeds , Logger); From c274481b6e173d55c9c6baa6e353e60dba33a24d Mon Sep 17 00:00:00 2001 From: Merl111 Date: Thu, 14 Oct 2021 17:34:11 +0200 Subject: [PATCH 09/10] fix, fix token creation --- Spook/Command/CommandDispatcher.Node.cs | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/Spook/Command/CommandDispatcher.Node.cs b/Spook/Command/CommandDispatcher.Node.cs index 9dcdd0c..cc8d7cd 100644 --- a/Spook/Command/CommandDispatcher.Node.cs +++ b/Spook/Command/CommandDispatcher.Node.cs @@ -277,9 +277,19 @@ protected void OnCreatePlatformToken(string[] args) return; } - tx = GenerateToken(_cli.NodeKeys, symbol, name, maxSupply, decimals, - TokenFlags.Fungible | TokenFlags.Transferable | TokenFlags.Divisible - | TokenFlags.Burnable); + var flags = TokenFlags.Fungible | TokenFlags.Transferable | TokenFlags.Burnable; + + if (decimals > 0) + { + flags = flags | TokenFlags.Divisible; + } + + if (maxSupply > 0) + { + flags = flags | TokenFlags.Finite; + } + + tx = GenerateToken(_cli.NodeKeys, symbol, name, maxSupply, decimals, flags); } else { From 2365c8347aec02b68192c565b47489a5847c3eee Mon Sep 17 00:00:00 2001 From: Merl111 Date: Fri, 5 Nov 2021 14:00:41 +0100 Subject: [PATCH 10/10] fixed median calculation --- Spook/Interop/NeoInterop.cs | 6 ++++++ Spook/Utils/SpookUtils.cs | 12 ++++++------ 2 files changed, 12 insertions(+), 6 deletions(-) diff --git a/Spook/Interop/NeoInterop.cs b/Spook/Interop/NeoInterop.cs index 145ff42..d5d92fd 100644 --- a/Spook/Interop/NeoInterop.cs +++ b/Spook/Interop/NeoInterop.cs @@ -595,6 +595,12 @@ public static InteropTransaction MakeInteropTx(Logger logger, NeoTx tx, NeoAPI a break; } + if (entry.data == null || entry.data.Length == 0) + { + logger.Debug("Ignore tx, invalid data field: " + tx); + return emptyTx; + } + if (pos == 1) { amount = PBigInteger.FromUnsignedArray(entry.data, true); diff --git a/Spook/Utils/SpookUtils.cs b/Spook/Utils/SpookUtils.cs index fbf7530..0888695 100644 --- a/Spook/Utils/SpookUtils.cs +++ b/Spook/Utils/SpookUtils.cs @@ -171,7 +171,7 @@ public static decimal GetNormalizedFee(FeeUrl[] fees) results.Add(task.Result); } - var median = GetMedian(results.ToArray()); + var median = GetMedian(results.ToArray()); return median; } @@ -206,12 +206,12 @@ public static decimal GetFee(FeeUrl feeObj) return fee; } - public static T GetMedian(T[] sourceArray) where T : IComparable + public static decimal GetMedian(decimal[] sourceArray) { if (sourceArray == null || sourceArray.Length == 0) throw new ArgumentException("Median of empty array not defined."); - T[] sortedArray = sourceArray; + decimal[] sortedArray = sourceArray; Array.Sort(sortedArray); //get the median @@ -222,10 +222,10 @@ public static T GetMedian(T[] sourceArray) where T : IComparable return sortedArray[mid]; } - dynamic value1 = sortedArray[mid]; - dynamic value2 = sortedArray[mid - 1]; + decimal value1 = sortedArray[mid]; + decimal value2 = sortedArray[mid - 1]; - return (sortedArray[mid] + value2) * 0.5; + return (value1 + value2) * 0.5M; } } }