private bool IsSystemTransaction(Transaction transaction) { var systemTransactionMethodNameList = _coreTransactionMethodNameListProvider.GetSystemTransactionMethodNameList(); var consensusContractAddress = _smartContractAddressService.GetAddressByContractName( SmartContractConstants.ConsensusContractSystemName); if (transaction.To == consensusContractAddress && systemTransactionMethodNameList.Contains(transaction.MethodName)) { return(true); } var tokenContractAddress = _smartContractAddressService.GetAddressByContractName(SmartContractConstants.TokenContractSystemName); if (transaction.To == tokenContractAddress && systemTransactionMethodNameList.Contains(transaction.MethodName)) { return(true); } var crossChainContractAddress = _smartContractAddressService.GetAddressByContractName(SmartContractConstants .CrossChainContractSystemName); if (transaction.To == crossChainContractAddress && systemTransactionMethodNameList.Contains(transaction.MethodName)) { return(true); } return(false); }
public bool ValidateTransaction(Transaction transaction, Hash blockHash) { var constrainedTransaction = new Lazy <List <string> >(() => _coreTransactionMethodNameListProvider.GetSystemTransactionMethodNameList()); if (transaction.To == _consensusContractAddress && constrainedTransaction.Value.Contains(transaction.MethodName)) { if (!_alreadyHas.ContainsKey(blockHash)) { _alreadyHas.TryAdd(blockHash, transaction); return(true); } if (_alreadyHas[blockHash].GetHash() == transaction.GetHash()) { // Validate twice or more. return(true); } _alreadyHas.TryRemove(blockHash, out var oldTransaction); Logger.LogError( $"Only allow one AEDPoS Contract core transaction.\nNew tx: {transaction}\nOld tx: {oldTransaction}"); return(false); } return(true); }
public async Task <IEnumerable <Transaction> > GetPreTransactionsAsync( IReadOnlyList <ServiceDescriptor> descriptors, ITransactionContext transactionContext) { try { var context = _contextService.Create(); var systemContractAddresses = new List <Address> { context.GetZeroSmartContractAddress(context.ChainId), context.GetContractAddressByName(TokenSmartContractAddressNameProvider.Name), // TODO: Try to use contract address name providers - put providers to one place easy to ref. context.GetContractAddressByName(Hash.FromString("AElf.ContractNames.Consensus")), context.GetContractAddressByName(Hash.FromString("AElf.ContractNames.CrossChain")), context.GetContractAddressByName(Hash.FromString("AElf.ContractNames.Economic")), }; if (systemContractAddresses.Contains(transactionContext.Transaction.To)) { if (_systemTransactionMethodNameListProvider.GetSystemTransactionMethodNameList() .Contains(transactionContext.Transaction.MethodName)) { return(new List <Transaction>()); } var methodNameWhiteList = new List <string> { nameof(TokenContractContainer.TokenContractStub.Create), nameof(TokenContractContainer.TokenContractStub.Issue), nameof(TokenContractContainer.TokenContractStub.CrossChainTransfer), nameof(TokenContractContainer.TokenContractStub.CrossChainReceiveToken), "IssueNativeToken" }; if (methodNameWhiteList.Contains(transactionContext.Transaction.MethodName)) { return(new List <Transaction>()); } } context.TransactionContext = transactionContext; var tokenContractAddress = context.GetContractAddressByName(TokenSmartContractAddressNameProvider.Name); if (context.CurrentHeight < Constants.GenesisBlockHeight + 1 || tokenContractAddress == null) { return(new List <Transaction>()); } if (!IsAcs1(descriptors) && transactionContext.Transaction.To != tokenContractAddress) { return(new List <Transaction>()); } var tokenStub = new TokenContractContainer.TokenContractStub { __factory = new TransactionGeneratingOnlyMethodStubFactory { Sender = transactionContext.Transaction.From, ContractAddress = tokenContractAddress } }; if (transactionContext.Transaction.To == tokenContractAddress && transactionContext.Transaction.MethodName == nameof(tokenStub.ChargeTransactionFees)) { // Skip ChargeTransactionFees itself return(new List <Transaction>()); } var unitPrice = await _transactionSizeFeeUnitPriceProvider.GetUnitPriceAsync(); var chargeFeeTransaction = (await tokenStub.ChargeTransactionFees.SendAsync( new ChargeTransactionFeesInput { MethodName = transactionContext.Transaction.MethodName, ContractAddress = transactionContext.Transaction.To, TransactionSizeFee = unitPrice * transactionContext.Transaction.Size(), PrimaryTokenSymbol = await _primaryTokenSymbolProvider.GetPrimaryTokenSymbol() })).Transaction; return(new List <Transaction> { chargeFeeTransaction }); } catch (Exception e) { Logger.LogError("Failed to generate ChargeTransactionFees tx.", e); throw; } }