| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461 |
- #!/usr/bin/env bash
- set -e
- cd "$(dirname "$0")"/../..
- set -x
- deployMethod="$1"
- nodeType="$2"
- entrypointIp="$3"
- numNodes="$4"
- if [[ -n $5 ]]; then
- export RUST_LOG="$5"
- fi
- skipSetup="$6"
- failOnValidatorBootupFailure="$7"
- externalPrimordialAccountsFile="$8"
- maybeDisableAirdrops="$9"
- internalNodesStakeLamports="${10}"
- internalNodesLamports="${11}"
- nodeIndex="${12}"
- numBenchTpsClients="${13}"
- benchTpsExtraArgs="${14}"
- genesisOptions="${15}"
- extraNodeArgs="${16}"
- maybeWarpSlot="${17}"
- maybeFullRpc="${18}"
- waitForNodeInit="${19}"
- extraPrimordialStakes="${20:=0}"
- tmpfsAccounts="${21:false}"
- disableQuic="${22}"
- enableUdp="${23}"
- maybeWenRestart="${24}"
- set +x
- missing() {
- echo "Error: $1 not specified"
- exit 1
- }
- [[ -n $deployMethod ]] || missing deployMethod
- [[ -n $nodeType ]] || missing nodeType
- [[ -n $entrypointIp ]] || missing entrypointIp
- [[ -n $numNodes ]] || missing numNodes
- [[ -n $skipSetup ]] || missing skipSetup
- [[ -n $failOnValidatorBootupFailure ]] || missing failOnValidatorBootupFailure
- airdropsEnabled=true
- if [[ -n $maybeDisableAirdrops ]]; then
- airdropsEnabled=false
- fi
- cat > deployConfig <<EOF
- deployMethod="$deployMethod"
- entrypointIp="$entrypointIp"
- numNodes="$numNodes"
- failOnValidatorBootupFailure=$failOnValidatorBootupFailure
- genesisOptions="$genesisOptions"
- airdropsEnabled=$airdropsEnabled
- EOF
- source net/common.sh
- source multinode-demo/common.sh
- loadConfigFile
- initCompleteFile=init-complete-node.log
- cat > ~/solana/on-reboot <<EOF
- #!/usr/bin/env bash
- cd ~/solana
- source scripts/oom-score-adj.sh
- now=\$(date -u +"%Y-%m-%dT%H:%M:%SZ")
- ln -sfT validator.log.\$now validator.log
- EOF
- chmod +x ~/solana/on-reboot
- case $deployMethod in
- local|tar|skip)
- PATH="$HOME"/.cargo/bin:"$PATH"
- export USE_INSTALL=1
- ./fetch-perf-libs.sh
- cat >> ~/solana/on-reboot <<EOF
- PATH="$HOME"/.cargo/bin:"$PATH"
- export USE_INSTALL=1
- (
- sudo SOLANA_METRICS_CONFIG="$SOLANA_METRICS_CONFIG" scripts/oom-monitor.sh
- ) > oom-monitor.log 2>&1 &
- echo \$! > oom-monitor.pid
- scripts/fd-monitor.sh > fd-monitor.log 2>&1 &
- echo \$! > fd-monitor.pid
- scripts/net-stats.sh > net-stats.log 2>&1 &
- echo \$! > net-stats.pid
- scripts/iftop.sh > iftop.log 2>&1 &
- echo \$! > iftop.pid
- scripts/system-stats.sh > system-stats.log 2>&1 &
- echo \$! > system-stats.pid
- EOF
- case $nodeType in
- bootstrap-validator)
- set -x
- if [[ $skipSetup != true ]]; then
- clear_config_dir "$SOLANA_CONFIG_DIR"
- if [[ -n $internalNodesLamports ]]; then
- echo "---" >> config/validator-balances.yml
- fi
- setupValidatorKeypair() {
- declare name=$1
- if [[ -f net/keypairs/"$name".json ]]; then
- cp net/keypairs/"$name".json config/"$name".json
- if [[ "$name" =~ ^validator-identity- ]]; then
- name="${name//-identity-/-vote-}"
- cp net/keypairs/"$name".json config/"$name".json
- name="${name//-vote-/-stake-}"
- cp net/keypairs/"$name".json config/"$name".json
- fi
- else
- solana-keygen new --no-passphrase -so config/"$name".json
- if [[ "$name" =~ ^validator-identity- ]]; then
- name="${name//-identity-/-vote-}"
- solana-keygen new --no-passphrase -so config/"$name".json
- name="${name//-vote-/-stake-}"
- solana-keygen new --no-passphrase -so config/"$name".json
- fi
- fi
- if [[ -n $internalNodesLamports ]]; then
- declare pubkey
- pubkey="$(solana-keygen pubkey config/"$name".json)"
- cat >> config/validator-balances.yml <<EOF
- $pubkey:
- balance: $internalNodesLamports
- owner: 11111111111111111111111111111111
- data:
- executable: false
- EOF
- fi
- }
- for i in $(seq 1 "$numNodes"); do
- setupValidatorKeypair validator-identity-"$i"
- done
- setupValidatorKeypair blockstreamer-identity
- lamports_per_signature="42"
- # shellcheck disable=SC2206 # Do not want to quote $genesisOptions
- genesis_args=($genesisOptions)
- for i in "${!genesis_args[@]}"; do
- if [[ "${genesis_args[$i]}" = --target-lamports-per-signature ]]; then
- lamports_per_signature="${genesis_args[$((i+1))]}"
- break
- fi
- done
- for i in $(seq 0 $((numBenchTpsClients-1))); do
- # shellcheck disable=SC2086 # Do not want to quote $benchTpsExtraArgs
- solana-bench-tps --write-client-keys config/bench-tps"$i".yml \
- --target-lamports-per-signature "$lamports_per_signature" $benchTpsExtraArgs
- # Skip first line, as it contains header
- tail -n +2 -q config/bench-tps"$i".yml >> config/client-accounts.yml
- echo "" >> config/client-accounts.yml
- done
- if [[ -f $externalPrimordialAccountsFile ]]; then
- cat "$externalPrimordialAccountsFile" >> config/validator-balances.yml
- fi
- if [[ -f config/validator-balances.yml ]]; then
- genesisOptions+=" --primordial-accounts-file config/validator-balances.yml"
- fi
- if [[ -f config/client-accounts.yml ]]; then
- genesisOptions+=" --primordial-accounts-file config/client-accounts.yml"
- fi
- if [[ -n $internalNodesStakeLamports ]]; then
- args+=(--bootstrap-validator-stake-lamports "$internalNodesStakeLamports")
- fi
- if [[ -n $internalNodesLamports ]]; then
- args+=(--bootstrap-validator-lamports "$internalNodesLamports")
- fi
- # shellcheck disable=SC2206 # Do not want to quote $genesisOptions
- args+=($genesisOptions)
- if [[ -f net/keypairs/faucet.json ]]; then
- export FAUCET_KEYPAIR=net/keypairs/faucet.json
- fi
- if [[ -f net/keypairs/bootstrap-validator-identity.json ]]; then
- export BOOTSTRAP_VALIDATOR_IDENTITY_KEYPAIR=net/keypairs/bootstrap-validator-identity.json
- fi
- if [[ -f net/keypairs/bootstrap-validator-stake.json ]]; then
- export BOOTSTRAP_VALIDATOR_STAKE_KEYPAIR=net/keypairs/bootstrap-validator-stake.json
- fi
- if [[ -f net/keypairs/bootstrap-validator-vote.json ]]; then
- export BOOTSTRAP_VALIDATOR_VOTE_KEYPAIR=net/keypairs/bootstrap-validator-vote.json
- fi
- echo "remote-node.sh: Primordial stakes: $extraPrimordialStakes"
- if [[ "$extraPrimordialStakes" -gt 0 ]]; then
- if [[ "$extraPrimordialStakes" -gt "$numNodes" ]]; then
- echo "warning: extraPrimordialStakes($extraPrimordialStakes) clamped to numNodes($numNodes)"
- extraPrimordialStakes=$numNodes
- fi
- for i in $(seq "$extraPrimordialStakes"); do
- args+=(--bootstrap-validator "$(solana-keygen pubkey "config/validator-identity-$i.json")"
- "$(solana-keygen pubkey "config/validator-vote-$i.json")"
- "$(solana-keygen pubkey "config/validator-stake-$i.json")"
- )
- done
- fi
- multinode-demo/setup.sh "${args[@]}"
- maybeWaitForSupermajority=
- # shellcheck disable=SC2086 # Do not want to quote $extraNodeArgs
- set -- $extraNodeArgs
- while [[ -n $1 ]]; do
- if [[ $1 = "--wait-for-supermajority" ]]; then
- maybeWaitForSupermajority=$2
- break
- fi
- shift
- done
- if [[ -z "$maybeWarpSlot" && -n "$maybeWaitForSupermajority" ]]; then
- maybeWarpSlot="--warp-slot $maybeWaitForSupermajority"
- fi
- if [[ -n "$maybeWarpSlot" ]]; then
- # shellcheck disable=SC2086 # Do not want to quote $maybeWarSlot
- agave-ledger-tool -l config/bootstrap-validator create-snapshot 0 config/bootstrap-validator $maybeWarpSlot
- fi
- agave-ledger-tool -l config/bootstrap-validator shred-version --max-genesis-archive-unpacked-size 1073741824 | tee config/shred-version
- if [[ -n "$maybeWaitForSupermajority" ]]; then
- bankHash=$(agave-ledger-tool -l config/bootstrap-validator verify --halt-at-slot 0 --print-bank-hash --output json | jq -r ".hash")
- shredVersion="$(cat "$SOLANA_CONFIG_DIR"/shred-version)"
- extraNodeArgs="$extraNodeArgs --expected-bank-hash $bankHash --expected-shred-version $shredVersion"
- echo "$bankHash" > config/bank-hash
- fi
- fi
- args=(
- --bind-address "$entrypointIp"
- --gossip-port 8001
- --init-complete-file "$initCompleteFile"
- )
- if [[ "$tmpfsAccounts" = "true" ]]; then
- args+=(--accounts /mnt/solana-accounts)
- fi
- if $maybeFullRpc; then
- args+=(--enable-rpc-transaction-history)
- args+=(--enable-extended-tx-metadata-storage)
- fi
- if $disableQuic; then
- args+=(--tpu-disable-quic)
- fi
- if $enableUdp; then
- args+=(--tpu-enable-udp)
- fi
- if [[ $airdropsEnabled = true ]]; then
- cat >> ~/solana/on-reboot <<EOF
- ./multinode-demo/faucet.sh > faucet.log 2>&1 &
- EOF
- fi
- if [[ -n "$maybeWenRestart" ]]; then
- args+=(--wen-restart "$maybeWenRestart")
- fi
- # shellcheck disable=SC2206 # Don't want to double quote $extraNodeArgs
- args+=($extraNodeArgs)
- cat >> ~/solana/on-reboot <<EOF
- nohup ./multinode-demo/bootstrap-validator.sh ${args[@]} > validator.log.\$now 2>&1 &
- pid=\$!
- oom_score_adj "\$pid" 1000
- disown
- EOF
- ~/solana/on-reboot
- if $waitForNodeInit; then
- net/remote/remote-node-wait-init.sh 600
- fi
- ;;
- validator|blockstreamer)
- if [[ $deployMethod != skip ]]; then
- net/scripts/rsync-retry.sh -vPrc "$entrypointIp":~/.cargo/bin/ ~/.cargo/bin/
- net/scripts/rsync-retry.sh -vPrc "$entrypointIp":~/version.yml ~/version.yml
- fi
- if [[ $skipSetup != true ]]; then
- clear_config_dir "$SOLANA_CONFIG_DIR"
- if [[ $nodeType = blockstreamer ]]; then
- net/scripts/rsync-retry.sh -vPrc \
- "$entrypointIp":~/solana/config/blockstreamer-identity.json "$SOLANA_CONFIG_DIR"/validator-identity.json
- else
- net/scripts/rsync-retry.sh -vPrc \
- "$entrypointIp":~/solana/config/validator-identity-"$nodeIndex".json "$SOLANA_CONFIG_DIR"/validator-identity.json
- net/scripts/rsync-retry.sh -vPrc \
- "$entrypointIp":~/solana/config/validator-stake-"$nodeIndex".json "$SOLANA_CONFIG_DIR"/stake-account.json
- net/scripts/rsync-retry.sh -vPrc \
- "$entrypointIp":~/solana/config/validator-vote-"$nodeIndex".json "$SOLANA_CONFIG_DIR"/vote-account.json
- fi
- net/scripts/rsync-retry.sh -vPrc \
- "$entrypointIp":~/solana/config/shred-version "$SOLANA_CONFIG_DIR"/shred-version
- net/scripts/rsync-retry.sh -vPrc \
- "$entrypointIp":~/solana/config/bank-hash "$SOLANA_CONFIG_DIR"/bank-hash || true
- net/scripts/rsync-retry.sh -vPrc \
- "$entrypointIp":~/solana/config/faucet.json "$SOLANA_CONFIG_DIR"/faucet.json
- fi
- args=(
- --entrypoint "$entrypointIp:8001"
- --gossip-port 8001
- --rpc-port 8899
- --expected-shred-version "$(cat "$SOLANA_CONFIG_DIR"/shred-version)"
- )
- if [[ $nodeType = blockstreamer ]]; then
- args+=(
- --blockstream /tmp/solana-blockstream.sock
- --no-voting
- --dev-no-sigverify
- --enable-rpc-transaction-history
- )
- else
- if [[ -n $internalNodesLamports ]]; then
- args+=(--node-lamports "$internalNodesLamports")
- fi
- fi
- if [[ ! -f "$SOLANA_CONFIG_DIR"/validator-identity.json ]]; then
- solana-keygen new --no-passphrase -so "$SOLANA_CONFIG_DIR"/validator-identity.json
- fi
- args+=(--identity "$SOLANA_CONFIG_DIR"/validator-identity.json)
- if [[ ! -f "$SOLANA_CONFIG_DIR"/vote-account.json ]]; then
- solana-keygen new --no-passphrase -so "$SOLANA_CONFIG_DIR"/vote-account.json
- fi
- args+=(--vote-account "$SOLANA_CONFIG_DIR"/vote-account.json)
- if [[ $airdropsEnabled != true ]]; then
- args+=(--no-airdrop)
- else
- args+=(--rpc-faucet-address "$entrypointIp:9900")
- fi
- if [[ -r "$SOLANA_CONFIG_DIR"/bank-hash ]]; then
- args+=(--expected-bank-hash "$(cat "$SOLANA_CONFIG_DIR"/bank-hash)")
- fi
- set -x
- # Add the faucet keypair to validators for convenient access from tools
- # like bench-tps and add to blocktreamers to run a faucet
- scp "$entrypointIp":~/solana/config/faucet.json "$SOLANA_CONFIG_DIR"/
- if [[ $nodeType = blockstreamer ]]; then
- # Run another faucet with the same keypair on the blockstreamer node.
- # Typically the blockstreamer node has a static IP/DNS name for hosting
- # the blockexplorer web app, and is a location that somebody would expect
- # to be able to airdrop from
- if [[ $airdropsEnabled = true ]]; then
- cat >> ~/solana/on-reboot <<EOF
- multinode-demo/faucet.sh > faucet.log 2>&1 &
- EOF
- fi
- # Grab the TLS cert generated by /certbot-restore.sh
- if [[ -f /.cert.pem ]]; then
- sudo install -o $UID -m 400 /.cert.pem /.key.pem .
- ls -l .cert.pem .key.pem
- fi
- fi
- args+=(--init-complete-file "$initCompleteFile")
- # shellcheck disable=SC2206 # Don't want to double quote $extraNodeArgs
- args+=($extraNodeArgs)
- maybeSkipAccountsCreation=
- if [[ $nodeIndex -le $extraPrimordialStakes ]]; then
- maybeSkipAccountsCreation="export SKIP_ACCOUNTS_CREATION=1"
- fi
- if [[ "$tmpfsAccounts" = "true" ]]; then
- args+=(--accounts /mnt/solana-accounts)
- fi
- if $maybeFullRpc; then
- args+=(--enable-rpc-transaction-history)
- args+=(--enable-extended-tx-metadata-storage)
- fi
- if $disableQuic; then
- args+=(--tpu-disable-quic)
- fi
- if $enableUdp; then
- args+=(--tpu-enable-udp)
- fi
- if [[ -n "$maybeWenRestart" ]]; then
- args+=(--wen-restart wen_restart.proto3)
- args+=(--wen-restart-coordinator "$maybeWenRestart")
- fi
- cat >> ~/solana/on-reboot <<EOF
- $maybeSkipAccountsCreation
- nohup multinode-demo/validator.sh ${args[@]} > validator.log.\$now 2>&1 &
- pid=\$!
- oom_score_adj "\$pid" 1000
- disown
- EOF
- ~/solana/on-reboot
- if $waitForNodeInit; then
- net/remote/remote-node-wait-init.sh 600
- fi
- if [[ $skipSetup != true && $nodeType != blockstreamer && -z $maybeSkipAccountsCreation ]]; then
- # Wait for the validator to catch up to the bootstrap validator before
- # delegating stake to it
- solana --url http://"$entrypointIp":8899 catchup config/validator-identity.json
- args=(
- --url http://"$entrypointIp":8899
- )
- if [[ $airdropsEnabled != true ]]; then
- args+=(--no-airdrop)
- fi
- if [[ -f config/validator-identity.json ]]; then
- args+=(--keypair config/validator-identity.json)
- fi
- if [[ ${extraPrimordialStakes} -eq 0 ]]; then
- echo "0 Primordial stakes, staking with $internalNodesStakeLamports"
- multinode-demo/delegate-stake.sh --vote-account "$SOLANA_CONFIG_DIR"/vote-account.json \
- --stake-account "$SOLANA_CONFIG_DIR"/stake-account.json \
- --force \
- "${args[@]}" "$internalNodesStakeLamports"
- else
- echo "Skipping staking with extra stakes: ${extraPrimordialStakes}"
- fi
- fi
- ;;
- *)
- echo "Error: unknown node type: $nodeType"
- exit 1
- ;;
- esac
- ;;
- *)
- echo "Unknown deployment method: $deployMethod"
- exit 1
- esac
|