diff --git a/.github/workflows/bench.yml b/.github/workflows/bench.yml index 71f2fc2135..c6710de7e2 100644 --- a/.github/workflows/bench.yml +++ b/.github/workflows/bench.yml @@ -11,7 +11,7 @@ jobs: - uses: actions/checkout@v4 - uses: actions/setup-go@v4 with: - go-version: "~1.22.8" + go-version: "~1.23.6" - run: go mod download shell: bash - run: ./scripts/build_bench_precompiles.sh diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 19cfb30a91..f0f5a7a888 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -24,7 +24,7 @@ jobs: - name: Set up Go uses: actions/setup-go@v5 with: - go-version: "~1.22.8" + go-version: "~1.23.6" - name: Set up arm64 cross compiler run: | sudo apt-get -y update diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index dfd3f0358c..479877a8b9 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -9,7 +9,7 @@ on: pull_request: env: - min_go_version: "~1.22.8" + min_go_version: "~1.23.6" jobs: lint_test: @@ -25,7 +25,7 @@ jobs: - name: golangci-lint uses: golangci/golangci-lint-action@v3 with: - version: v1.56 + version: v1.63 working-directory: . args: --timeout 10m skip-pkg-cache: true diff --git a/.golangci.yml b/.golangci.yml index c6c8d5748a..ace8a22dad 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -3,11 +3,6 @@ run: timeout: 10m tests: true - # default is true. Enables skipping of directories: - # vendor$, third_party$, testdata$, examples$, Godeps$, builtin$ - skip-dirs-use-default: true - # Include non-test files tagged as test-only. - # Context: https://github.com/ava-labs/avalanchego/pull/3173 linters: disable-all: true @@ -18,8 +13,19 @@ linters: - ineffassign - misspell - unconvert + - typecheck - unused + # - staticcheck + - bidichk + - durationcheck + - copyloopvar - whitespace + # - revive # only certain checks enabled + - durationcheck + - gocheckcompilerdirectives + - reassign + - mirror + - tenv linters-settings: gofmt: diff --git a/Dockerfile b/Dockerfile index c4e2f97757..7312954822 100644 --- a/Dockerfile +++ b/Dockerfile @@ -5,7 +5,7 @@ ARG AVALANCHEGO_NODE_IMAGE # ============= Compilation Stage ================ -FROM --platform=$BUILDPLATFORM golang:1.22.8-bullseye AS builder +FROM --platform=$BUILDPLATFORM golang:1.23.6-bullseye AS builder WORKDIR /build @@ -14,7 +14,7 @@ WORKDIR /build COPY go.mod go.sum avalanchego* ./ # Download avalanche dependencies using go mod -RUN go mod download && go mod tidy -compat=1.22 +RUN go mod download && go mod tidy -compat=1.23 # Copy the code into the container COPY . . diff --git a/README.md b/README.md index 5b1d910030..ec8c8dd99d 100644 --- a/README.md +++ b/README.md @@ -59,7 +59,7 @@ To support these changes, there have been a number of changes to the SubnetEVM b ### Clone Subnet-evm -First install Go 1.22.8 or later. Follow the instructions [here](https://go.dev/doc/install). You can verify by running `go version`. +First install Go 1.23.6 or later. Follow the instructions [here](https://go.dev/doc/install). You can verify by running `go version`. Set `$GOPATH` environment variable properly for Go to look for Go Workspaces. Please read [this](https://go.dev/doc/code) for details. You can verify by running `echo $GOPATH`. diff --git a/RELEASES.md b/RELEASES.md index b3e1654d4b..b7eb6ea301 100644 --- a/RELEASES.md +++ b/RELEASES.md @@ -1,7 +1,8 @@ # Release Notes ## Pending Release - +* Bump golang version to v1.23.6 +* Bump golangci-lint to v1.63 and add linters * Refactored trie_prefetcher.go to be structurally similar to upstream. * Remove legacy gossip handler and metrics diff --git a/accounts/abi/abi_test.go b/accounts/abi/abi_test.go index 68052e639a..023ff5cc4e 100644 --- a/accounts/abi/abi_test.go +++ b/accounts/abi/abi_test.go @@ -1210,7 +1210,6 @@ func TestUnpackRevert(t *testing.T) { {"4e487b7100000000000000000000000000000000000000000000000000000000000000ff", "unknown panic code: 0xff", nil}, } for index, c := range cases { - index, c := index, c t.Run(fmt.Sprintf("case %d", index), func(t *testing.T) { t.Parallel() got, err := UnpackRevert(common.Hex2Bytes(c.input)) diff --git a/accounts/abi/bind/bind.go b/accounts/abi/bind/bind.go index a4dd0963d7..eb82a9fb42 100644 --- a/accounts/abi/bind/bind.go +++ b/accounts/abi/bind/bind.go @@ -266,7 +266,7 @@ func BindHelper(types []string, abis []string, bytecodes []string, fsigs []map[s } // Parse library references. for pattern, name := range libs { - matched, err := regexp.Match("__\\$"+pattern+"\\$__", []byte(contracts[types[i]].InputBin)) + matched, err := regexp.MatchString("__\\$"+pattern+"\\$__", contracts[types[i]].InputBin) if err != nil { log.Error("Could not search for pattern", "pattern", pattern, "contract", contracts[types[i]], "err", err) } diff --git a/accounts/abi/bind/bind_test.go b/accounts/abi/bind/bind_test.go index 9179e369c4..9adc39f62c 100644 --- a/accounts/abi/bind/bind_test.go +++ b/accounts/abi/bind/bind_test.go @@ -2179,7 +2179,7 @@ func golangBindings(t *testing.T, overload bool) { if out, err := replacer.CombinedOutput(); err != nil { t.Fatalf("failed to replace binding test dependency to current source tree: %v\n%s", err, out) } - tidier := exec.Command(gocmd, "mod", "tidy", "-compat=1.22") + tidier := exec.Command(gocmd, "mod", "tidy", "-compat=1.23") tidier.Dir = pkg if out, err := tidier.CombinedOutput(); err != nil { t.Fatalf("failed to tidy Go module file: %v\n%s", err, out) diff --git a/accounts/abi/bind/precompilebind/precompile_bind_test.go b/accounts/abi/bind/precompilebind/precompile_bind_test.go index f12170dede..2158160d3a 100644 --- a/accounts/abi/bind/precompilebind/precompile_bind_test.go +++ b/accounts/abi/bind/precompilebind/precompile_bind_test.go @@ -695,7 +695,7 @@ func TestPrecompileBind(t *testing.T) { if out, err := replacer.CombinedOutput(); err != nil { t.Fatalf("failed to replace binding test dependency to current source tree: %v\n%s", err, out) } - tidier := exec.Command(gocmd, "mod", "tidy", "-compat=1.22") + tidier := exec.Command(gocmd, "mod", "tidy", "-compat=1.23") tidier.Dir = pkg if out, err := tidier.CombinedOutput(); err != nil { t.Fatalf("failed to tidy Go module file: %v\n%s", err, out) diff --git a/accounts/abi/event_test.go b/accounts/abi/event_test.go index a967decd52..4a254e9950 100644 --- a/accounts/abi/event_test.go +++ b/accounts/abi/event_test.go @@ -341,7 +341,6 @@ func TestEventTupleUnpack(t *testing.T) { for _, tc := range testCases { assert := assert.New(t) - tc := tc t.Run(tc.name, func(t *testing.T) { err := unpackTestEventData(tc.dest, tc.data, tc.jsonLog, assert) if tc.error == "" { diff --git a/accounts/abi/pack_test.go b/accounts/abi/pack_test.go index 47d4931698..b13de922a5 100644 --- a/accounts/abi/pack_test.go +++ b/accounts/abi/pack_test.go @@ -44,7 +44,6 @@ import ( func TestPack(t *testing.T) { t.Parallel() for i, test := range packUnpackTests { - i, test := i, test t.Run(strconv.Itoa(i), func(t *testing.T) { t.Parallel() encb, err := hex.DecodeString(test.packed) diff --git a/accounts/abi/reflect_test.go b/accounts/abi/reflect_test.go index 5d90cdb763..624032968d 100644 --- a/accounts/abi/reflect_test.go +++ b/accounts/abi/reflect_test.go @@ -182,7 +182,6 @@ var reflectTests = []reflectTest{ func TestReflectNameToStruct(t *testing.T) { t.Parallel() for _, test := range reflectTests { - test := test t.Run(test.name, func(t *testing.T) { t.Parallel() m, err := mapArgNamesToStructFields(test.args, reflect.ValueOf(test.struc)) diff --git a/accounts/abi/topics_test.go b/accounts/abi/topics_test.go index 70522b6ce6..53e4327bf6 100644 --- a/accounts/abi/topics_test.go +++ b/accounts/abi/topics_test.go @@ -147,7 +147,6 @@ func TestMakeTopics(t *testing.T) { }, } for _, tt := range tests { - tt := tt t.Run(tt.name, func(t *testing.T) { t.Parallel() got, err := MakeTopics(tt.args.query...) @@ -383,7 +382,6 @@ func TestParseTopics(t *testing.T) { tests := setupTopicsTests() for _, tt := range tests { - tt := tt t.Run(tt.name, func(t *testing.T) { t.Parallel() createObj := tt.args.createObj() @@ -403,7 +401,6 @@ func TestParseTopicsIntoMap(t *testing.T) { tests := setupTopicsTests() for _, tt := range tests { - tt := tt t.Run(tt.name, func(t *testing.T) { t.Parallel() outMap := make(map[string]interface{}) diff --git a/accounts/abi/unpack_test.go b/accounts/abi/unpack_test.go index 0b4224efa5..d7f383a731 100644 --- a/accounts/abi/unpack_test.go +++ b/accounts/abi/unpack_test.go @@ -399,7 +399,6 @@ func TestMethodMultiReturn(t *testing.T) { "Can not unpack into a slice with wrong types", }} for _, tc := range testCases { - tc := tc t.Run(tc.name, func(t *testing.T) { require := require.New(t) err := abi.UnpackIntoInterface(tc.dest, "multi", data) @@ -957,7 +956,7 @@ func TestOOMMaliciousInput(t *testing.T) { } encb, err := hex.DecodeString(test.enc) if err != nil { - t.Fatalf("invalid hex: %s" + test.enc) + t.Fatalf("invalid hex: %s", test.enc) } _, err = abi.Methods["method"].Outputs.UnpackValues(encb) if err == nil { diff --git a/cmd/evm/t8n_test.go b/cmd/evm/t8n_test.go index 2304a54af6..9f653cebea 100644 --- a/cmd/evm/t8n_test.go +++ b/cmd/evm/t8n_test.go @@ -429,7 +429,7 @@ func TestT9n(t *testing.T) { ok, err := cmpJson(have, want) switch { case err != nil: - t.Logf(string(have)) + t.Log(string(have)) t.Fatalf("test %d, json parsing failed: %v", i, err) case !ok: t.Fatalf("test %d: output wrong, have \n%v\nwant\n%v\n", i, string(have), string(want)) @@ -561,7 +561,7 @@ func TestB11r(t *testing.T) { ok, err := cmpJson(have, want) switch { case err != nil: - t.Logf(string(have)) + t.Log(string(have)) t.Fatalf("test %d, json parsing failed: %v", i, err) case !ok: t.Fatalf("test %d: output wrong, have \n%v\nwant\n%v\n", i, string(have), string(want)) diff --git a/cmd/simulator/load/loader.go b/cmd/simulator/load/loader.go index 0dffe80bb7..8a5c5d0c93 100644 --- a/cmd/simulator/load/loader.go +++ b/cmd/simulator/load/loader.go @@ -66,7 +66,6 @@ func (l *Loader[T]) Execute(ctx context.Context) error { log.Info("Starting tx agents...") eg := errgroup.Group{} for _, agent := range agents { - agent := agent eg.Go(func() error { return agent.Execute(ctx) }) @@ -100,8 +99,6 @@ func (l *Loader[T]) ConfirmReachedTip(ctx context.Context) error { eg := errgroup.Group{} for i, client := range l.clients { - i := i - client := client eg.Go(func() error { for { latestHeight, err := client.LatestHeight(ctx) diff --git a/core/blockchain_test.go b/core/blockchain_test.go index 83b4938080..4b9534996a 100644 --- a/core/blockchain_test.go +++ b/core/blockchain_test.go @@ -293,7 +293,6 @@ func TestBlockChainOfflinePruningUngracefulShutdown(t *testing.T) { return createBlockChain(db, pruningConfig, gspec, lastAcceptedHash) } for _, tt := range tests { - tt := tt t.Run(tt.Name, func(t *testing.T) { t.Parallel() tt.testFunc(t, create) diff --git a/core/predicate_check_test.go b/core/predicate_check_test.go index 85e685154e..d31bbf0fd8 100644 --- a/core/predicate_check_test.go +++ b/core/predicate_check_test.go @@ -293,7 +293,6 @@ func TestCheckPredicate(t *testing.T) { expectedErr: ErrIntrinsicGas, }, } { - test := test t.Run(name, func(t *testing.T) { require := require.New(t) // Create the rules from TestChainConfig and update the predicates based on the test params diff --git a/core/rawdb/accessors_chain_test.go b/core/rawdb/accessors_chain_test.go index b9e1eddb4d..eaac8d546b 100644 --- a/core/rawdb/accessors_chain_test.go +++ b/core/rawdb/accessors_chain_test.go @@ -291,10 +291,10 @@ func TestBlockReceiptStorage(t *testing.T) { // Insert the receipt slice into the database and check presence WriteReceipts(db, hash, 0, receipts) if rs := ReadReceipts(db, hash, 0, 0, params.TestChainConfig); len(rs) == 0 { - t.Fatalf("no receipts returned") + t.Fatal("no receipts returned") } else { if err := checkReceiptsRLP(rs, receipts); err != nil { - t.Fatalf(err.Error()) + t.Fatal(err) } } // Delete the body and ensure that the receipts are no longer returned (metadata can't be recomputed) @@ -308,7 +308,7 @@ func TestBlockReceiptStorage(t *testing.T) { } // Ensure that receipts without metadata can be returned without the block body too if err := checkReceiptsRLP(ReadRawReceipts(db, hash, 0), receipts); err != nil { - t.Fatalf(err.Error()) + t.Fatal(err) } // Sanity check that body and header alone without the receipt is a full purge WriteHeader(db, header) diff --git a/core/types/transaction_test.go b/core/types/transaction_test.go index 4471a6ba45..02ea3d16a4 100644 --- a/core/types/transaction_test.go +++ b/core/types/transaction_test.go @@ -520,9 +520,7 @@ func TestYParityJSONUnmarshalling(t *testing.T) { DynamicFeeTxType, BlobTxType, } { - txType := txType for _, test := range tests { - test := test t.Run(fmt.Sprintf("txType=%d: %s", txType, test.name), func(t *testing.T) { // Copy the base json testJson := make(map[string]interface{}) diff --git a/eth/filters/api.go b/eth/filters/api.go index 0748822b97..ba551b1b39 100644 --- a/eth/filters/api.go +++ b/eth/filters/api.go @@ -350,7 +350,6 @@ func (api *FilterAPI) Logs(ctx context.Context, crit FilterCriteria) (*rpc.Subsc select { case logs := <-matchedLogs: for _, log := range logs { - log := log notifier.Notify(rpcSub.ID, &log) } case <-rpcSub.Err(): // client send an unsubscribe request diff --git a/eth/tracers/internal/tracetest/calltrace_test.go b/eth/tracers/internal/tracetest/calltrace_test.go index f2cbeed762..61e41d2526 100644 --- a/eth/tracers/internal/tracetest/calltrace_test.go +++ b/eth/tracers/internal/tracetest/calltrace_test.go @@ -113,7 +113,6 @@ func testCallTracer(tracerName string, dirPath string, t *testing.T) { if !strings.HasSuffix(file.Name(), ".json") { continue } - file := file // capture range variable t.Run(camel(strings.TrimSuffix(file.Name(), ".json")), func(t *testing.T) { t.Parallel() @@ -205,7 +204,6 @@ func BenchmarkTracers(b *testing.B) { if !strings.HasSuffix(file.Name(), ".json") { continue } - file := file // capture range variable b.Run(camel(strings.TrimSuffix(file.Name(), ".json")), func(b *testing.B) { blob, err := os.ReadFile(filepath.Join("testdata", "call_tracer", file.Name())) if err != nil { diff --git a/eth/tracers/internal/tracetest/flat_calltrace_test.go b/eth/tracers/internal/tracetest/flat_calltrace_test.go index 93b85735e6..3f6a626711 100644 --- a/eth/tracers/internal/tracetest/flat_calltrace_test.go +++ b/eth/tracers/internal/tracetest/flat_calltrace_test.go @@ -168,7 +168,6 @@ func testFlatCallTracer(tracerName string, dirPath string, t *testing.T) { if !strings.HasSuffix(file.Name(), ".json") { continue } - file := file // capture range variable t.Run(camel(strings.TrimSuffix(file.Name(), ".json")), func(t *testing.T) { t.Parallel() diff --git a/eth/tracers/internal/tracetest/prestate_test.go b/eth/tracers/internal/tracetest/prestate_test.go index ef7c5cfd20..fcc48d5189 100644 --- a/eth/tracers/internal/tracetest/prestate_test.go +++ b/eth/tracers/internal/tracetest/prestate_test.go @@ -83,7 +83,6 @@ func testPrestateDiffTracer(tracerName string, dirPath string, t *testing.T) { if !strings.HasSuffix(file.Name(), ".json") { continue } - file := file // capture range variable t.Run(camel(strings.TrimSuffix(file.Name(), ".json")), func(t *testing.T) { t.Parallel() diff --git a/eth/tracers/logger/logger.go b/eth/tracers/logger/logger.go index 5aa4327434..863510d2c0 100644 --- a/eth/tracers/logger/logger.go +++ b/eth/tracers/logger/logger.go @@ -446,7 +446,7 @@ func formatLogs(logs []StructLog) []StructLogRes { } formatted[index].Stack = &stack } - if trace.ReturnData != nil && len(trace.ReturnData) > 0 { + if len(trace.ReturnData) > 0 { formatted[index].ReturnData = hexutil.Bytes(trace.ReturnData).String() } if trace.Memory != nil { diff --git a/go.mod b/go.mod index a6e7041f37..e8af45695b 100644 --- a/go.mod +++ b/go.mod @@ -1,11 +1,11 @@ module github.com/ava-labs/subnet-evm -go 1.22.8 +go 1.23.6 require ( github.com/VictoriaMetrics/fastcache v1.12.1 github.com/antithesishq/antithesis-sdk-go v0.3.8 - github.com/ava-labs/avalanchego v1.12.2 + github.com/ava-labs/avalanchego v1.12.3-0.20250218154446-f1ec9a13b90a github.com/cespare/cp v0.1.0 github.com/crate-crypto/go-ipa v0.0.0-20231025140028-3c0104f4b233 github.com/davecgh/go-spew v1.1.1 @@ -55,7 +55,7 @@ require ( require ( github.com/DataDog/zstd v1.5.2 // indirect github.com/NYTimes/gziphandler v1.1.1 // indirect - github.com/ava-labs/coreth v0.14.1-rc.1 // indirect + github.com/ava-labs/coreth v0.14.1-rc.1.0.20250217192834-6060a4a6a6d3 // indirect github.com/beorn7/perks v1.0.1 // indirect github.com/bits-and-blooms/bitset v1.10.0 // indirect github.com/btcsuite/btcd/btcec/v2 v2.3.2 // indirect diff --git a/go.sum b/go.sum index cb8666e5e8..f5f6740c90 100644 --- a/go.sum +++ b/go.sum @@ -60,10 +60,10 @@ github.com/antithesishq/antithesis-sdk-go v0.3.8/go.mod h1:IUpT2DPAKh6i/YhSbt6Gl github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8= github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5 h1:0CwZNZbxp69SHPdPJAN/hZIm0C4OItdklCFmMRWYpio= github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5/go.mod h1:wHh0iHkYZB8zMSxRWpUBQtwG5a7fFgvEO+odwuTv2gs= -github.com/ava-labs/avalanchego v1.12.2 h1:vZroUgB5xMMczDQnw9etDD1XhZsejFlKky+ZZv8wOKc= -github.com/ava-labs/avalanchego v1.12.2/go.mod h1:uEDLbAUPcGCfDWW680rVfysEofUe/jWte5qQk0j5hMs= -github.com/ava-labs/coreth v0.14.1-rc.1 h1:U72XlRm/fKyASmjThsWzfO/ZRvu1kaONFaX+KdJNxIc= -github.com/ava-labs/coreth v0.14.1-rc.1/go.mod h1:lxDSXLcrszMo0N/PVJzfZ//H+bRwXF/KQWtpEYgXZqM= +github.com/ava-labs/avalanchego v1.12.3-0.20250218154446-f1ec9a13b90a h1:cBuGdwpaB1TBnfHS0w7oJyBJlM2UGOS4CEioxqMCG2g= +github.com/ava-labs/avalanchego v1.12.3-0.20250218154446-f1ec9a13b90a/go.mod h1:pgUuh27zaeaXeMiIqqu/OWpbAhJQkYMJMft6nxXG9FE= +github.com/ava-labs/coreth v0.14.1-rc.1.0.20250217192834-6060a4a6a6d3 h1:0OrQidq+b3kb7KlnDqc5mkB/73i1zxYEMiXioWSU4+w= +github.com/ava-labs/coreth v0.14.1-rc.1.0.20250217192834-6060a4a6a6d3/go.mod h1:/XrU+CAm/0wiY5Ui05TLj2/n+czbCV6/Qrw/UMWp5aI= github.com/aymerick/raymond v2.0.3-0.20180322193309-b565731e1464+incompatible/go.mod h1:osfaiScAUVup+UC9Nfq76eWqDhXlp+4UYaA8uhTBO6g= github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM= github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= diff --git a/internal/flags/flags_test.go b/internal/flags/flags_test.go index ce78870dcd..294c8149e9 100644 --- a/internal/flags/flags_test.go +++ b/internal/flags/flags_test.go @@ -27,7 +27,6 @@ package flags import ( - "os" "os/user" "runtime" "testing" @@ -61,7 +60,7 @@ func TestPathExpansion(t *testing.T) { } } - os.Setenv(`DDDXXX`, `/tmp`) + t.Setenv(`DDDXXX`, `/tmp`) for test, expected := range tests { got := expandPath(test) if got != expected { diff --git a/plugin/evm/vm_warp_test.go b/plugin/evm/vm_warp_test.go index 5a448c8ce4..03e30932a9 100644 --- a/plugin/evm/vm_warp_test.go +++ b/plugin/evm/vm_warp_test.go @@ -22,6 +22,7 @@ import ( avagoUtils "github.com/ava-labs/avalanchego/utils" "github.com/ava-labs/avalanchego/utils/constants" "github.com/ava-labs/avalanchego/utils/crypto/bls" + "github.com/ava-labs/avalanchego/utils/crypto/bls/signer/localsigner" "github.com/ava-labs/avalanchego/utils/set" "github.com/ava-labs/avalanchego/vms/components/chain" avalancheWarp "github.com/ava-labs/avalanchego/vms/platformvm/warp" @@ -280,13 +281,13 @@ func testWarpVMTransaction(t *testing.T, unsignedMessage *avalancheWarp.Unsigned defer logsSub.Unsubscribe() nodeID1 := ids.GenerateTestNodeID() - blsSecretKey1, err := bls.NewSigner() + blsSecretKey1, err := localsigner.New() require.NoError(err) blsPublicKey1 := blsSecretKey1.PublicKey() blsSignature1 := blsSecretKey1.Sign(unsignedMessage.Bytes()) nodeID2 := ids.GenerateTestNodeID() - blsSecretKey2, err := bls.NewSigner() + blsSecretKey2, err := localsigner.New() require.NoError(err) blsPublicKey2 := blsSecretKey2.PublicKey() blsSignature2 := blsSecretKey2.Sign(unsignedMessage.Bytes()) @@ -550,7 +551,7 @@ func testReceiveWarpMessage( weight uint64 } newSigner := func(networkID ids.ID, weight uint64) signer { - secret, err := bls.NewSigner() + secret, err := localsigner.New() require.NoError(err) return signer{ networkID: networkID, diff --git a/plugin/runner/runner.go b/plugin/runner/runner.go index 9b5b5efe29..fbccd72057 100644 --- a/plugin/runner/runner.go +++ b/plugin/runner/runner.go @@ -22,7 +22,7 @@ func Run(versionStr string) { os.Exit(1) } if printVersion && versionStr != "" { - fmt.Printf(versionStr) + fmt.Print(versionStr) os.Exit(0) } if err := ulimit.Set(ulimit.DefaultFDLimit, logging.NoLog{}); err != nil { diff --git a/precompile/contracts/warp/config.go b/precompile/contracts/warp/config.go index feede8eb44..3668ead9c8 100644 --- a/precompile/contracts/warp/config.go +++ b/precompile/contracts/warp/config.go @@ -31,16 +31,17 @@ var ( ) var ( - errOverflowSignersGasCost = errors.New("overflow calculating warp signers gas cost") - errInvalidPredicateBytes = errors.New("cannot unpack predicate bytes") - errInvalidWarpMsg = errors.New("cannot unpack warp message") - errCannotParseWarpMsg = errors.New("cannot parse warp message") - errInvalidWarpMsgPayload = errors.New("cannot unpack warp message payload") - errInvalidAddressedPayload = errors.New("cannot unpack addressed payload") - errInvalidBlockHashPayload = errors.New("cannot unpack block hash payload") - errCannotGetNumSigners = errors.New("cannot fetch num signers from warp message") - errWarpCannotBeActivated = errors.New("warp cannot be activated before Durango") - errFailedVerification = errors.New("cannot verify warp signature") + errOverflowSignersGasCost = errors.New("overflow calculating warp signers gas cost") + errInvalidPredicateBytes = errors.New("cannot unpack predicate bytes") + errInvalidWarpMsg = errors.New("cannot unpack warp message") + errCannotParseWarpMsg = errors.New("cannot parse warp message") + errInvalidWarpMsgPayload = errors.New("cannot unpack warp message payload") + errInvalidAddressedPayload = errors.New("cannot unpack addressed payload") + errInvalidBlockHashPayload = errors.New("cannot unpack block hash payload") + errCannotGetNumSigners = errors.New("cannot fetch num signers from warp message") + errWarpCannotBeActivated = errors.New("warp cannot be activated before Durango") + errFailedVerification = errors.New("cannot verify warp signature") + errCannotRetrieveValidatorSet = errors.New("cannot retrieve validator set") ) // Config implements the precompileconfig.Config interface and @@ -208,16 +209,25 @@ func (c *Config) VerifyPredicate(predicateContext *precompileconfig.PredicateCon warpMsg.SourceChainID, c.RequirePrimaryNetworkSigners, ) - err = warpMsg.Signature.Verify( + + validatorSet, err := warp.GetCanonicalValidatorSetFromChainID( context.Background(), - &warpMsg.UnsignedMessage, - predicateContext.SnowCtx.NetworkID, state, predicateContext.ProposerVMBlockCtx.PChainHeight, + warpMsg.UnsignedMessage.SourceChainID, + ) + if err != nil { + log.Debug("failed to retrieve canonical validator set", "msgID", warpMsg.ID(), "err", err) + return fmt.Errorf("%w: %w", errCannotRetrieveValidatorSet, err) + } + + err = warpMsg.Signature.Verify( + &warpMsg.UnsignedMessage, + predicateContext.SnowCtx.NetworkID, + validatorSet, quorumNumerator, WarpQuorumDenominator, ) - if err != nil { log.Debug("failed to verify warp signature", "msgID", warpMsg.ID(), "err", err) return fmt.Errorf("%w: %w", errFailedVerification, err) diff --git a/precompile/contracts/warp/contract_test.go b/precompile/contracts/warp/contract_test.go index 4565df0ef8..6c4c06001c 100644 --- a/precompile/contracts/warp/contract_test.go +++ b/precompile/contracts/warp/contract_test.go @@ -11,7 +11,6 @@ import ( "github.com/ava-labs/avalanchego/ids" agoUtils "github.com/ava-labs/avalanchego/utils" "github.com/ava-labs/avalanchego/utils/set" - "github.com/ava-labs/avalanchego/vms/platformvm/warp" avalancheWarp "github.com/ava-labs/avalanchego/vms/platformvm/warp" "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" "github.com/ava-labs/subnet-evm/core/state" @@ -96,7 +95,7 @@ func TestSendWarpMessage(t *testing.T) { sendWarpMessagePayload, ) require.NoError(t, err) - unsignedWarpMessage, err := warp.NewUnsignedMessage( + unsignedWarpMessage, err := avalancheWarp.NewUnsignedMessage( defaultSnowCtx.NetworkID, blockchainID, sendWarpMessageAddressedPayload.Bytes(), @@ -747,7 +746,7 @@ func TestPackEvents(t *testing.T) { ) require.NoError(t, err) - unsignedWarpMessage, err := warp.NewUnsignedMessage( + unsignedWarpMessage, err := avalancheWarp.NewUnsignedMessage( networkID, sourceChainID, addressedPayload.Bytes(), diff --git a/precompile/contracts/warp/predicate_test.go b/precompile/contracts/warp/predicate_test.go index 65d202de09..35afb24ed9 100644 --- a/precompile/contracts/warp/predicate_test.go +++ b/precompile/contracts/warp/predicate_test.go @@ -17,6 +17,7 @@ import ( agoUtils "github.com/ava-labs/avalanchego/utils" "github.com/ava-labs/avalanchego/utils/constants" "github.com/ava-labs/avalanchego/utils/crypto/bls" + "github.com/ava-labs/avalanchego/utils/crypto/bls/signer/localsigner" "github.com/ava-labs/avalanchego/utils/set" avalancheWarp "github.com/ava-labs/avalanchego/vms/platformvm/warp" "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" @@ -111,7 +112,7 @@ func (v *testValidator) Compare(o *testValidator) int { } func newTestValidator() *testValidator { - sk, err := bls.NewSigner() + sk, err := localsigner.New() if err != nil { panic(err) } diff --git a/precompile/contracts/warp/signature_verification_test.go b/precompile/contracts/warp/signature_verification_test.go index d52f0a0f89..90ee808f91 100644 --- a/precompile/contracts/warp/signature_verification_test.go +++ b/precompile/contracts/warp/signature_verification_test.go @@ -19,12 +19,13 @@ import ( ) type signatureTest struct { - name string - stateF func(*gomock.Controller) validators.State - quorumNum uint64 - quorumDen uint64 - msgF func(*require.Assertions) *avalancheWarp.Message - err error + name string + stateF func(*gomock.Controller) validators.State + quorumNum uint64 + quorumDen uint64 + msgF func(*require.Assertions) *avalancheWarp.Message + verifyErr error + canonicalErr error } // This test copies the test coverage from https://github.com/ava-labs/avalanchego/blob/0117ab96/vms/platformvm/warp/signature_test.go#L137. @@ -55,7 +56,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: errTest, + canonicalErr: errTest, }, { name: "can't get validator set", @@ -82,7 +83,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: errTest, + canonicalErr: errTest, }, { name: "weight overflow", @@ -122,7 +123,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrWeightOverflow, + canonicalErr: avalancheWarp.ErrWeightOverflow, }, { name: "invalid bit set index", @@ -152,7 +153,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrInvalidBitSet, + verifyErr: avalancheWarp.ErrInvalidBitSet, }, { name: "unknown index", @@ -185,7 +186,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrUnknownValidator, + verifyErr: avalancheWarp.ErrUnknownValidator, }, { name: "insufficient weight", @@ -229,7 +230,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrInsufficientWeight, + verifyErr: avalancheWarp.ErrInsufficientWeight, }, { name: "can't parse sig", @@ -263,7 +264,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrParseSignature, + verifyErr: avalancheWarp.ErrParseSignature, }, { name: "no validators", @@ -298,7 +299,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: bls.ErrNoPublicKeys, + verifyErr: bls.ErrNoPublicKeys, }, { name: "invalid signature (substitute)", @@ -342,7 +343,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrInvalidSignature, + verifyErr: avalancheWarp.ErrInvalidSignature, }, { name: "invalid signature (missing one)", @@ -382,7 +383,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrInvalidSignature, + verifyErr: avalancheWarp.ErrInvalidSignature, }, { name: "invalid signature (extra one)", @@ -427,7 +428,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: avalancheWarp.ErrInvalidSignature, + verifyErr: avalancheWarp.ErrInvalidSignature, }, { name: "valid signature", @@ -471,7 +472,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: nil, + verifyErr: nil, }, { name: "valid signature (boundary)", @@ -515,7 +516,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: nil, + verifyErr: nil, }, { name: "valid signature (missing key)", @@ -576,7 +577,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: nil, + verifyErr: nil, }, { name: "valid signature (duplicate key)", @@ -635,7 +636,7 @@ func TestSignatureVerification(t *testing.T) { require.NoError(err) return msg }, - err: nil, + verifyErr: nil, }, } @@ -648,16 +649,24 @@ func TestSignatureVerification(t *testing.T) { msg := tt.msgF(require) pChainState := tt.stateF(ctrl) - err := msg.Signature.Verify( + validatorSet, err := avalancheWarp.GetCanonicalValidatorSetFromChainID( context.Background(), - &msg.UnsignedMessage, - networkID, pChainState, pChainHeight, + msg.UnsignedMessage.SourceChainID, + ) + require.ErrorIs(err, tt.canonicalErr) + if err != nil { + return + } + err = msg.Signature.Verify( + &msg.UnsignedMessage, + networkID, + validatorSet, tt.quorumNum, tt.quorumDen, ) - require.ErrorIs(err, tt.err) + require.ErrorIs(err, tt.verifyErr) }) } } diff --git a/rpc/client_test.go b/rpc/client_test.go index eec18afb8f..97bc69e61b 100644 --- a/rpc/client_test.go +++ b/rpc/client_test.go @@ -723,7 +723,6 @@ func TestClientHTTP(t *testing.T) { ) defer client.Close() for i := range results { - i := i go func() { errc <- client.Call(&results[i], "test_echo", wantResult.String, wantResult.Int, wantResult.Args) }() diff --git a/rpc/types_test.go b/rpc/types_test.go index a255c1e9f7..779b23296f 100644 --- a/rpc/types_test.go +++ b/rpc/types_test.go @@ -145,7 +145,6 @@ func TestBlockNumberOrHash_WithNumber_MarshalAndUnmarshal(t *testing.T) { {"earliest", int64(EarliestBlockNumber)}, } for _, test := range tests { - test := test t.Run(test.name, func(t *testing.T) { bnh := BlockNumberOrHashWithNumber(BlockNumber(test.number)) marshalled, err := json.Marshal(bnh) diff --git a/scripts/lint.sh b/scripts/lint.sh index 643291d934..acd5b324fc 100755 --- a/scripts/lint.sh +++ b/scripts/lint.sh @@ -4,11 +4,10 @@ set -o errexit set -o nounset set -o pipefail -# Upstream is compatible with v1.54.x at time of this writing, and +# Upstream is compatible with v1.63.x at time of this writing, and # checking for this specific version is an attempt to avoid skew -# between local and CI execution. The latest version (v1.55.1) seems -# to cause spurious failures -KNOWN_GOOD_VERSION="v1.56" +# between local and CI execution. +KNOWN_GOOD_VERSION="v1.63" VERSION="$(golangci-lint --version | sed -e 's+golangci-lint has version \(v1.*\)\..* built.*+\1+')" if [[ "${VERSION}" != "${KNOWN_GOOD_VERSION}" ]]; then echo "expected golangci-lint ${KNOWN_GOOD_VERSION}, but ${VERSION} was used" diff --git a/scripts/versions.sh b/scripts/versions.sh index 2f0a46f660..2b27dadefc 100644 --- a/scripts/versions.sh +++ b/scripts/versions.sh @@ -4,5 +4,5 @@ # shellcheck disable=SC2034 # Don't export them as they're used in the context of other calls -AVALANCHE_VERSION=${AVALANCHE_VERSION:-'v1.12.2'} +AVALANCHE_VERSION=${AVALANCHE_VERSION:-'f1ec9a13'} GINKGO_VERSION=${GINKGO_VERSION:-'v2.2.0'} diff --git a/utils/snow.go b/utils/snow.go index fe33a56512..f89b9cffdf 100644 --- a/utils/snow.go +++ b/utils/snow.go @@ -14,7 +14,7 @@ import ( "github.com/ava-labs/avalanchego/snow/validators/validatorstest" "github.com/ava-labs/avalanchego/upgrade/upgradetest" "github.com/ava-labs/avalanchego/utils/constants" - "github.com/ava-labs/avalanchego/utils/crypto/bls" + "github.com/ava-labs/avalanchego/utils/crypto/bls/signer/localsigner" "github.com/ava-labs/avalanchego/utils/logging" "github.com/ava-labs/avalanchego/vms/platformvm/warp" ) @@ -26,7 +26,7 @@ var ( ) func TestSnowContext() *snow.Context { - sk, err := bls.NewSigner() + sk, err := localsigner.New() if err != nil { panic(err) } diff --git a/warp/aggregator/aggregator_test.go b/warp/aggregator/aggregator_test.go index 055d3edfa8..397e39553d 100644 --- a/warp/aggregator/aggregator_test.go +++ b/warp/aggregator/aggregator_test.go @@ -14,11 +14,12 @@ import ( "github.com/ava-labs/avalanchego/ids" "github.com/ava-labs/avalanchego/utils/crypto/bls" + "github.com/ava-labs/avalanchego/utils/crypto/bls/signer/localsigner" avalancheWarp "github.com/ava-labs/avalanchego/vms/platformvm/warp" ) func newValidator(t testing.TB, weight uint64) (bls.Signer, *avalancheWarp.Validator) { - sk, err := bls.NewSigner() + sk, err := localsigner.New() require.NoError(t, err) pk := sk.PublicKey() return sk, &avalancheWarp.Validator{ @@ -51,7 +52,7 @@ func TestAggregateSignatures(t *testing.T) { vdr2: sig2, vdr3: sig3, } - nonVdrSk, err := bls.NewSigner() + nonVdrSk, err := localsigner.New() require.NoError(t, err) nonVdrSig := nonVdrSk.Sign(unsignedMsg.Bytes()) vdrs := []*avalancheWarp.Validator{ diff --git a/warp/backend_test.go b/warp/backend_test.go index 764957882c..cee1150353 100644 --- a/warp/backend_test.go +++ b/warp/backend_test.go @@ -12,7 +12,7 @@ import ( "github.com/ava-labs/avalanchego/database/memdb" "github.com/ava-labs/avalanchego/ids" "github.com/ava-labs/avalanchego/utils" - "github.com/ava-labs/avalanchego/utils/crypto/bls" + "github.com/ava-labs/avalanchego/utils/crypto/bls/signer/localsigner" avalancheWarp "github.com/ava-labs/avalanchego/vms/platformvm/warp" "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" "github.com/ava-labs/subnet-evm/warp/warptest" @@ -41,7 +41,7 @@ func init() { func TestAddAndGetValidMessage(t *testing.T) { db := memdb.New() - sk, err := bls.NewSigner() + sk, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(sk, networkID, sourceChainID) messageSignatureCache := &cache.LRU[ids.ID, []byte]{Size: 500} @@ -64,7 +64,7 @@ func TestAddAndGetValidMessage(t *testing.T) { func TestAddAndGetUnknownMessage(t *testing.T) { db := memdb.New() - sk, err := bls.NewSigner() + sk, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(sk, networkID, sourceChainID) messageSignatureCache := &cache.LRU[ids.ID, []byte]{Size: 500} @@ -83,7 +83,7 @@ func TestGetBlockSignature(t *testing.T) { blockClient := warptest.MakeBlockClient(blkID) db := memdb.New() - sk, err := bls.NewSigner() + sk, err := localsigner.New() require.NoError(err) warpSigner := avalancheWarp.NewSigner(sk, networkID, sourceChainID) messageSignatureCache := &cache.LRU[ids.ID, []byte]{Size: 500} @@ -108,7 +108,7 @@ func TestGetBlockSignature(t *testing.T) { func TestZeroSizedCache(t *testing.T) { db := memdb.New() - sk, err := bls.NewSigner() + sk, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(sk, networkID, sourceChainID) @@ -136,7 +136,7 @@ func TestOffChainMessages(t *testing.T) { check func(require *require.Assertions, b Backend) err error } - sk, err := bls.NewSigner() + sk, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(sk, networkID, sourceChainID) diff --git a/warp/handlers/signature_request_test.go b/warp/handlers/signature_request_test.go index 79a27f1fff..15e6e661a0 100644 --- a/warp/handlers/signature_request_test.go +++ b/warp/handlers/signature_request_test.go @@ -11,6 +11,7 @@ import ( "github.com/ava-labs/avalanchego/database/memdb" "github.com/ava-labs/avalanchego/ids" "github.com/ava-labs/avalanchego/utils/crypto/bls" + "github.com/ava-labs/avalanchego/utils/crypto/bls/signer/localsigner" avalancheWarp "github.com/ava-labs/avalanchego/vms/platformvm/warp" "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" "github.com/ava-labs/subnet-evm/plugin/evm/message" @@ -26,7 +27,7 @@ func TestMessageSignatureHandler(t *testing.T) { database := memdb.New() snowCtx := utils.TestSnowContext() - blsSecretKey, err := bls.NewSigner() + blsSecretKey, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(blsSecretKey, snowCtx.NetworkID, snowCtx.ChainID) @@ -132,7 +133,7 @@ func TestBlockSignatureHandler(t *testing.T) { database := memdb.New() snowCtx := utils.TestSnowContext() - blsSecretKey, err := bls.NewSigner() + blsSecretKey, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(blsSecretKey, snowCtx.NetworkID, snowCtx.ChainID) diff --git a/warp/service.go b/warp/service.go index bcb54ccbbc..993b65b221 100644 --- a/warp/service.go +++ b/warp/service.go @@ -112,22 +112,22 @@ func (a *API) aggregateSignatures(ctx context.Context, unsignedMessage *warp.Uns } state := warpValidators.NewState(a.state, a.sourceSubnetID, a.sourceChainID, a.requirePrimaryNetworkSigners()) - validators, totalWeight, err := warp.GetCanonicalValidatorSet(ctx, state, pChainHeight, subnetID) + validatorSet, err := warp.GetCanonicalValidatorSetFromSubnetID(ctx, state, pChainHeight, subnetID) if err != nil { return nil, fmt.Errorf("failed to get validator set: %w", err) } - if len(validators) == 0 { + if len(validatorSet.Validators) == 0 { return nil, fmt.Errorf("%w (SubnetID: %s, Height: %d)", errNoValidators, subnetID, pChainHeight) } log.Debug("Fetching signature", "sourceSubnetID", subnetID, "height", pChainHeight, - "numValidators", len(validators), - "totalWeight", totalWeight, + "numValidators", len(validatorSet.Validators), + "totalWeight", validatorSet.TotalWeight, ) - agg := aggregator.New(aggregator.NewSignatureGetter(a.client), validators, totalWeight) + agg := aggregator.New(aggregator.NewSignatureGetter(a.client), validatorSet.Validators, validatorSet.TotalWeight) signatureResult, err := agg.AggregateSignatures(ctx, unsignedMessage, quorumNum) if err != nil { return nil, err diff --git a/warp/verifier_backend_test.go b/warp/verifier_backend_test.go index 6697e1f148..8b6b6ea518 100644 --- a/warp/verifier_backend_test.go +++ b/warp/verifier_backend_test.go @@ -14,7 +14,7 @@ import ( "github.com/ava-labs/avalanchego/network/p2p/acp118" "github.com/ava-labs/avalanchego/proto/pb/sdk" "github.com/ava-labs/avalanchego/snow/engine/common" - "github.com/ava-labs/avalanchego/utils/crypto/bls" + "github.com/ava-labs/avalanchego/utils/crypto/bls/signer/localsigner" "github.com/ava-labs/avalanchego/utils/timer/mockable" avalancheWarp "github.com/ava-labs/avalanchego/vms/platformvm/warp" "github.com/ava-labs/avalanchego/vms/platformvm/warp/payload" @@ -33,7 +33,7 @@ func TestAddressedCallSignatures(t *testing.T) { database := memdb.New() snowCtx := utils.TestSnowContext() - blsSecretKey, err := bls.NewSigner() + blsSecretKey, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(blsSecretKey, snowCtx.NetworkID, snowCtx.ChainID) @@ -149,7 +149,7 @@ func TestBlockSignatures(t *testing.T) { database := memdb.New() snowCtx := utils.TestSnowContext() - blsSecretKey, err := bls.NewSigner() + blsSecretKey, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(blsSecretKey, snowCtx.NetworkID, snowCtx.ChainID) @@ -267,7 +267,7 @@ func TestBlockSignatures(t *testing.T) { func TestUptimeSignatures(t *testing.T) { database := memdb.New() snowCtx := utils.TestSnowContext() - blsSecretKey, err := bls.NewSigner() + blsSecretKey, err := localsigner.New() require.NoError(t, err) warpSigner := avalancheWarp.NewSigner(blsSecretKey, snowCtx.NetworkID, snowCtx.ChainID)