Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Move read elf params #786

Merged
merged 8 commits into from
Jun 2, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion proxy-cli/info.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,8 @@

from proxy.common_neon.address import EthereumAddress, accountWithSeed
from proxy.common_neon.solana_interactor import SolanaInteractor
from proxy.environment import PERM_ACCOUNT_LIMIT, SOLANA_URL, get_solana_accounts
from proxy.common_neon.environment_utils import get_solana_accounts
from proxy.common_neon.environment_data import SOLANA_URL, PERM_ACCOUNT_LIMIT


class DecimalEncoder(json.JSONEncoder):
Expand Down
3 changes: 2 additions & 1 deletion proxy/airdropper/__init__.py
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
from .airdropper import Airdropper, AIRDROP_AMOUNT_SOL, NEON_PRICE_USD
from .airdropper import Airdropper, AIRDROP_AMOUNT_SOL
from ..common_neon.environment_data import NEON_PRICE_USD
from .airdropper_app import AirdropperApp
2 changes: 1 addition & 1 deletion proxy/airdropper/airdropper.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
from decimal import Decimal
from logged_groups import logged_group

from ..environment import NEON_PRICE_USD, EVM_LOADER_ID
from ..common_neon.environment_data import EVM_LOADER_ID, NEON_PRICE_USD
from ..common_neon.solana_interactor import SolanaInteractor
from ..indexer.indexer_base import IndexerBase
from ..indexer.pythnetwork import PythNetworkClient
Expand Down
2 changes: 1 addition & 1 deletion proxy/airdropper/airdropper_app.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
from logged_groups import logged_group
from solana.publickey import PublicKey

from ..environment import EVM_LOADER_ID
from ..common_neon.environment_data import EVM_LOADER_ID

from .airdropper import Airdropper

Expand Down
29 changes: 13 additions & 16 deletions proxy/common_neon/account_whitelist.py
Original file line number Diff line number Diff line change
@@ -1,19 +1,14 @@
import traceback
from datetime import datetime
from proxy.environment import ELF_PARAMS
from proxy.common_neon.permission_token import PermissionToken
from solana.publickey import PublicKey
from solana.account import Account as SolanaAccount
from typing import Union
from proxy.common_neon.address import EthereumAddress
from logged_groups import logged_group
from ..common_neon.elf_params import ElfParams
from ..common_neon.solana_interactor import SolanaInteractor

NEON_MINIMAL_CLIENT_ALLOWANCE_BALANCE = int(ELF_PARAMS.get("NEON_MINIMAL_CLIENT_ALLOWANCE_BALANCE", 0))
NEON_MINIMAL_CONTRACT_ALLOWANCE_BALANCE = int(ELF_PARAMS.get("NEON_MINIMAL_CONTRACT_ALLOWANCE_BALANCE", 0))
ALLOWANCE_TOKEN_ADDR = ELF_PARAMS.get("NEON_PERMISSION_ALLOWANCE_TOKEN", '')
DENIAL_TOKEN_ADDR = ELF_PARAMS.get("NEON_PERMISSION_DENIAL_TOKEN", '')


@logged_group("neon.AccountWhitelist")
class AccountWhitelist:
Expand All @@ -24,15 +19,17 @@ def __init__(self, solana: SolanaInteractor, permission_update_int: int):
self.allowance_token = None
self.denial_token = None

if ALLOWANCE_TOKEN_ADDR == '' and DENIAL_TOKEN_ADDR == '':
allowance_token_addr = ElfParams().allowance_token_addr
denial_token_addr = ElfParams().denial_token_addr
if allowance_token_addr == '' and denial_token_addr == '':
return

if ALLOWANCE_TOKEN_ADDR == '' or DENIAL_TOKEN_ADDR == '':
if allowance_token_addr == '' or denial_token_addr == '':
self.error(f'Wrong proxy configuration: allowance and denial tokens must both exist or absent!')
raise Exception("NEON service is unhealthy. Try again later")

self.allowance_token = PermissionToken(self.solana, PublicKey(ALLOWANCE_TOKEN_ADDR))
self.denial_token = PermissionToken(self.solana, PublicKey(DENIAL_TOKEN_ADDR))
self.allowance_token = PermissionToken(self.solana, PublicKey(allowance_token_addr))
self.denial_token = PermissionToken(self.solana, PublicKey(denial_token_addr))

def read_balance_diff(self, ether_addr: Union[str, EthereumAddress]) -> int:
token_list = [
Expand Down Expand Up @@ -78,16 +75,16 @@ def deprive_permissions(self, ether_addr: Union[str, EthereumAddress], min_balan
return False

def grant_client_permissions(self, ether_addr: Union[str, EthereumAddress]):
return self.grant_permissions(ether_addr, NEON_MINIMAL_CLIENT_ALLOWANCE_BALANCE)
return self.grant_permissions(ether_addr, ElfParams().neon_minimal_client_allowance_balance)

def grant_contract_permissions(self, ether_addr: Union[str, EthereumAddress]):
return self.grant_permissions(ether_addr, NEON_MINIMAL_CONTRACT_ALLOWANCE_BALANCE)
return self.grant_permissions(ether_addr, ElfParams().neon_minimal_contract_allowance_balance)

def deprive_client_permissions(self, ether_addr: Union[str, EthereumAddress]):
return self.deprive_permissions(ether_addr, NEON_MINIMAL_CLIENT_ALLOWANCE_BALANCE)
return self.deprive_permissions(ether_addr, ElfParams().neon_minimal_client_allowance_balance)

def deprive_contract_permissions(self, ether_addr: Union[str, EthereumAddress]):
return self.deprive_permissions(ether_addr, NEON_MINIMAL_CONTRACT_ALLOWANCE_BALANCE)
return self.deprive_permissions(ether_addr, ElfParams().neon_minimal_contract_allowance_balance)

def get_current_time(self):
return datetime.now().timestamp()
Expand Down Expand Up @@ -116,7 +113,7 @@ def has_permission(self, ether_addr: Union[str, EthereumAddress], min_balance: i
f'Type(err): {type(err)}, Error: {err}, Traceback: {err_tb}')

def has_client_permission(self, ether_addr: Union[str, EthereumAddress]):
return self.has_permission(ether_addr, NEON_MINIMAL_CLIENT_ALLOWANCE_BALANCE)
return self.has_permission(ether_addr, ElfParams().neon_minimal_client_allowance_balance)

def has_contract_permission(self, ether_addr: Union[str, EthereumAddress]):
return self.has_permission(ether_addr, NEON_MINIMAL_CONTRACT_ALLOWANCE_BALANCE)
return self.has_permission(ether_addr, ElfParams().neon_minimal_contract_allowance_balance)
7 changes: 3 additions & 4 deletions proxy/common_neon/address.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,9 @@
from hashlib import sha256
from solana.publickey import PublicKey

from .environment_data import EVM_LOADER_ID
from .constants import ACCOUNT_SEED_VERSION


class EthereumAddress:
def __init__(self, data, private: eth_keys.PrivateKey = None):
Expand Down Expand Up @@ -36,15 +39,11 @@ def __bytes__(self): return self.data


def accountWithSeed(base: bytes, seed: bytes) -> PublicKey:
from ..environment import EVM_LOADER_ID

result = PublicKey(sha256(bytes(base) + bytes(seed) + bytes(PublicKey(EVM_LOADER_ID))).digest())
return result


def ether2program(ether):
from .constants import ACCOUNT_SEED_VERSION
from ..environment import EVM_LOADER_ID

if isinstance(ether, str):
pass
Expand Down
9 changes: 6 additions & 3 deletions proxy/common_neon/compute_budget.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

from solana.transaction import TransactionInstruction, Transaction
from .constants import COMPUTE_BUDGET_ID
from ..environment import NEON_HEAP_FRAME, NEON_COMPUTE_UNITS, NEON_ADDITIONAL_FEE
from ..common_neon.elf_params import ElfParams
from typing import Union


Expand All @@ -27,8 +27,11 @@ def requestHeapFrame(heap_frame) -> TransactionInstruction:
class TransactionWithComputeBudget(Transaction):
def __init__(self, *args, **kwargs):
Transaction.__init__(self, *args, **kwargs)
self.instructions.append(ComputeBudget.requestUnits(NEON_COMPUTE_UNITS, NEON_ADDITIONAL_FEE))
self.instructions.append(ComputeBudget.requestHeapFrame(NEON_HEAP_FRAME))
compute_units = ElfParams().neon_compute_units
additional_fee = ElfParams().neon_additional_fee
self.instructions.append(ComputeBudget.requestUnits(compute_units, additional_fee))
heap_frame = ElfParams().neon_heap_frame
self.instructions.append(ComputeBudget.requestHeapFrame(heap_frame))

def add(self, *args: Union[Transaction, TransactionInstruction]) -> TransactionWithComputeBudget:
"""Add one or more instructions to this Transaction."""
Expand Down
84 changes: 84 additions & 0 deletions proxy/common_neon/elf_params.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
from __future__ import annotations

from typing import Optional

from logged_groups import logged_group
from singleton_decorator import singleton

from solana.publickey import PublicKey

from .environment_utils import neon_cli


@singleton
class ElfParams:

def __init__(self):
self.elf_params = {}
read_elf_params(self.elf_params)

@property
def collateral_pool_base(self) -> Optional[str]:
return self.elf_params.get("NEON_POOL_BASE")

@property
def neon_heap_frame(self) -> int:
return int(self.elf_params.get("NEON_HEAP_FRAME"))

@property
def neon_compute_units(self) -> int:
return int(self.elf_params.get("NEON_COMPUTE_UNITS"))

@property
def neon_additional_fee(self):
return int(self.elf_params.get("NEON_ADDITIONAL_FEE"))

@property
def neon_token_mint(self) -> PublicKey:
return PublicKey(self.elf_params.get("NEON_TOKEN_MINT"))

@property
def chain_id(self) -> int:
return int(self.elf_params.get('NEON_CHAIN_ID'))

@property
def holder_msg_size(self) -> int:
return int(self.elf_params.get("NEON_HOLDER_MSG_SIZE"))

@property
def neon_evm_version(self) -> Optional[str]:
return self.elf_params.get("NEON_PKG_VERSION")

@property
def neon_evm_revision(self) -> Optional[str]:
return self.elf_params.get('NEON_REVISION')

@property
def neon_gas_limit_multiplier_no_chainid(self) -> int:
return int(self.elf_params.get('NEON_GAS_LIMIT_MULTIPLIER_NO_CHAINID'))

@property
def neon_minimal_client_allowance_balance(self) -> int:
return int(self.elf_params.get("NEON_MINIMAL_CLIENT_ALLOWANCE_BALANCE", 0))

@property
def neon_minimal_contract_allowance_balance(self) -> int:
return int(self.elf_params.get("NEON_MINIMAL_CONTRACT_ALLOWANCE_BALANCE", 0))

@property
def allowance_token_addr(self) -> str:
return self.elf_params.get("NEON_PERMISSION_ALLOWANCE_TOKEN", '')

@property
def denial_token_addr(self) -> str:
return self.elf_params.get("NEON_PERMISSION_DENIAL_TOKEN", '')


@logged_group("neon.Proxy")
def read_elf_params(out_dict, *, logger):
logger.debug("Read ELF params")
for param in neon_cli().call("neon-elf-params").splitlines():
if param.startswith('NEON_') and '=' in param:
v = param.split('=')
out_dict[v[0]] = v[1]
logger.debug(f"ELF param: {v[0]}: {v[1]}")
7 changes: 5 additions & 2 deletions proxy/common_neon/emulator_interactor.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,9 @@
from typing import Optional, Dict, Any
from ..common_neon.eth_proto import Trx as NeonTrx

from ..environment import neon_cli, NEON_TOKEN_MINT, CHAIN_ID
from ..common_neon.elf_params import ElfParams

from .environment_utils import neon_cli
from .errors import EthereumError
from .types import NeonEmulatingResult

Expand Down Expand Up @@ -291,7 +292,9 @@ def emulator(contract, sender, data, value):
data = data or "none"
value = value or ""
try:
return neon_cli().call("emulate", "--token_mint", str(NEON_TOKEN_MINT), "--chain_id", str(CHAIN_ID), sender, contract, data, value)
neon_token_mint = ElfParams().neon_token_mint
chain_id = ElfParams().chain_id
return neon_cli().call("emulate", "--token_mint", str(neon_token_mint), "--chain_id", str(chain_id), sender, contract, data, value)
except subprocess.CalledProcessError as err:
msg, code = NeonCliErrorParser().execute('emulator', err)
raise EthereumError(message=msg, code=code)
53 changes: 53 additions & 0 deletions proxy/common_neon/environment_data.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
import os
from decimal import Decimal
from solana.publickey import PublicKey

SOLANA_URL = os.environ.get("SOLANA_URL", "http://localhost:8899")
PP_SOLANA_URL = os.environ.get("PP_SOLANA_URL", SOLANA_URL)
EVM_LOADER_ID = os.environ.get("EVM_LOADER")
neon_cli_timeout = float(os.environ.get("NEON_CLI_TIMEOUT", "0.5"))
CONFIRMATION_CHECK_DELAY = float(os.environ.get("NEON_CONFIRMATION_CHECK_DELAY", "0.1"))
CONTINUE_COUNT_FACTOR = int(os.environ.get("CONTINUE_COUNT_FACTOR", "3"))
TIMEOUT_TO_RELOAD_NEON_CONFIG = int(os.environ.get("TIMEOUT_TO_RELOAD_NEON_CONFIG", "3600"))

MINIMAL_GAS_PRICE = os.environ.get("MINIMAL_GAS_PRICE", None)
if MINIMAL_GAS_PRICE is not None:
MINIMAL_GAS_PRICE = int(MINIMAL_GAS_PRICE)*10**9
EXTRA_GAS = int(os.environ.get("EXTRA_GAS", "0"))
LOG_NEON_CLI_DEBUG = os.environ.get("LOG_NEON_CLI_DEBUG", "NO") == "YES"
USE_EARLIEST_BLOCK_IF_0_PASSED = os.environ.get("USE_EARLIEST_BLOCK_IF_0_PASSED", "NO") == "YES"
RETRY_ON_FAIL = int(os.environ.get("RETRY_ON_FAIL", "10"))
RETRY_ON_FAIL_ON_GETTING_CONFIRMED_TRANSACTION = max(int(os.environ.get("RETRY_ON_FAIL_ON_GETTING_CONFIRMED_TRANSACTION", "1000")), 1)
FUZZING_BLOCKHASH = os.environ.get("FUZZING_BLOCKHASH", "NO") == "YES"
CONFIRM_TIMEOUT = max(int(os.environ.get("CONFIRM_TIMEOUT", 10)), 10)
PARALLEL_REQUESTS = int(os.environ.get("PARALLEL_REQUESTS", 10))
HISTORY_START = "7BdwyUQ61RUZP63HABJkbW66beLk22tdXnP69KsvQBJekCPVaHoJY47Rw68b3VV1UbQNHxX3uxUSLfiJrfy2bTn"
INDEXER_POLL_COUNT = int(os.environ.get("INDEXER_POLL_COUNT", "1000"))
START_SLOT = os.environ.get('START_SLOT', 0)
INDEXER_RECEIPTS_COUNT_LIMIT = int(os.environ.get("INDEXER_RECEIPTS_COUNT_LIMIT", "1000"))
FINALIZED = os.environ.get('FINALIZED', 'finalized')
CANCEL_TIMEOUT = int(os.environ.get("CANCEL_TIMEOUT", 60))
SKIP_CANCEL_TIMEOUT = int(os.environ.get("CANCEL_TIMEOUT", 1000))
HOLDER_TIMEOUT = int(os.environ.get("HOLDER_TIMEOUT", "216000")) # 1 day by default
ACCOUNT_PERMISSION_UPDATE_INT = int(os.environ.get("ACCOUNT_PERMISSION_UPDATE_INT", 60 * 5))
PERM_ACCOUNT_LIMIT = max(int(os.environ.get("PERM_ACCOUNT_LIMIT", 2)), 2)
OPERATOR_FEE = Decimal(os.environ.get("OPERATOR_FEE", "0.1"))
GAS_PRICE_SUGGESTED_PCT = Decimal(os.environ.get("GAS_PRICE_SUGGEST_PCT", "0.05"))
NEON_PRICE_USD = Decimal('0.25')
SOL_PRICE_UPDATE_INTERVAL = int(os.environ.get("SOL_PRICE_UPDATE_INTERVAL", 60))
GET_SOL_PRICE_MAX_RETRIES = int(os.environ.get("GET_SOL_PRICE_MAX_RETRIES", 10))
GET_SOL_PRICE_RETRY_INTERVAL = int(os.environ.get("GET_SOL_PRICE_RETRY_INTERVAL", 1))
INDEXER_LOG_SKIP_COUNT = int(os.environ.get("INDEXER_LOG_SKIP_COUNT", 100))
RECHECK_RESOURCE_LIST_INTERVAL = int(os.environ.get('RECHECK_RESOURCE_LIST_INTERVAL', 60))
MIN_OPERATOR_BALANCE_TO_WARN = max(int(os.environ.get("MIN_OPERATOR_BALANCE_TO_WARN", 9000000000)), 9000000000)
MIN_OPERATOR_BALANCE_TO_ERR = max(int(os.environ.get("MIN_OPERATOR_BALANCE_TO_ERR", 1000000000)), 1000000000)
SKIP_PREFLIGHT = os.environ.get("SKIP_PREFLIGHT", "NO") == "YES"
CONTRACT_EXTRA_SPACE = int(os.environ.get("CONTRACT_EXTRA_SPACE", 2048))
EVM_STEP_COUNT = int(os.environ.get("EVM_STEP_COUNT", 750)) # number of evm-steps, performed by one iteration
ENABLE_PRIVATE_API = os.environ.get("ENABLE_PRIVATE_API", "NO") == "YES"
GATHER_STATISTICS = os.environ.get("GATHER_STATISTICS", "NO") == "YES"
ALLOW_UNDERPRICED_TX_WITHOUT_CHAINID = os.environ.get("ALLOW_UNDERPRICED_TX_WITHOUT_CHAINID", "NO") == "YES"
LOG_FULL_OBJECT_INFO = os.environ.get("LOG_FULL_OBJECT_INFO", "NO") == "YES"
PYTH_MAPPING_ACCOUNT = os.environ.get("PYTH_MAPPING_ACCOUNT", None)
if PYTH_MAPPING_ACCOUNT is not None:
PYTH_MAPPING_ACCOUNT = PublicKey(PYTH_MAPPING_ACCOUNT)
Loading