From 51c62ee1428165eac01e58618efe9185763d158d Mon Sep 17 00:00:00 2001 From: Dan Stough Date: Fri, 17 Feb 2023 15:04:12 -0500 Subject: [PATCH] [OSS] security: update go to 1.20.1 (#16263) * security: update go to 1.20.1 --- .changelog/16263.txt | 4 +++ GNUmakefile | 6 ++-- agent/agent_test.go | 5 ++-- agent/consul/auto_config_endpoint_test.go | 4 +-- agent/consul/internal_endpoint_test.go | 2 +- agent/consul/leader_peering_test.go | 4 +-- agent/consul/state/acl_test.go | 2 -- agent/coordinate_endpoint_test.go | 6 ++-- agent/prepared_query_endpoint_test.go | 21 +++++++------- agent/testagent.go | 5 ---- agent/txn_endpoint_test.go | 18 ++++++------ api/go.mod | 2 +- command/members/members_test.go | 3 -- lib/rand.go | 34 ----------------------- main.go | 5 ---- sdk/freeport/freeport.go | 1 - sdk/go.mod | 2 +- tlsutil/config_test.go | 2 +- 18 files changed, 41 insertions(+), 85 deletions(-) create mode 100644 .changelog/16263.txt delete mode 100644 lib/rand.go diff --git a/.changelog/16263.txt b/.changelog/16263.txt new file mode 100644 index 000000000000..a8cd3f9043af --- /dev/null +++ b/.changelog/16263.txt @@ -0,0 +1,4 @@ +```release-note:security +Upgrade to use Go 1.20.1. +This resolves vulnerabilities [CVE-2022-41724](https://go.dev/issue/58001) in `crypto/tls` and [CVE-2022-41723](https://go.dev/issue/57855) in `net/http`. +``` diff --git a/GNUmakefile b/GNUmakefile index 18345e5c1f03..e84118626e2f 100644 --- a/GNUmakefile +++ b/GNUmakefile @@ -7,11 +7,11 @@ SHELL = bash # These version variables can either be a valid string for "go install @" # or the string @DEV to imply use what is currently installed locally. ### -GOLANGCI_LINT_VERSION='v1.50.1' -MOCKERY_VERSION='v2.12.2' +GOLANGCI_LINT_VERSION='v1.51.1' +MOCKERY_VERSION='v2.20.0' BUF_VERSION='v1.4.0' PROTOC_GEN_GO_GRPC_VERSION="v1.2.0" -MOG_VERSION='v0.3.0' +MOG_VERSION='v0.4.0' PROTOC_GO_INJECT_TAG_VERSION='v1.3.0' PROTOC_GEN_GO_BINARY_VERSION="v0.0.1" DEEP_COPY_VERSION='bc3f5aa5735d8a54961580a3a24422c308c831c2' diff --git a/agent/agent_test.go b/agent/agent_test.go index 8b74394ee4dd..b4406f2142ca 100644 --- a/agent/agent_test.go +++ b/agent/agent_test.go @@ -4,13 +4,14 @@ import ( "bytes" "context" "crypto/md5" + "crypto/rand" "crypto/tls" "crypto/x509" "encoding/base64" "encoding/json" "fmt" "io/ioutil" - "math/rand" + mathrand "math/rand" "net" "net/http" "net/http/httptest" @@ -699,7 +700,7 @@ func testAgent_AddServices_AliasUpdateCheckNotReverted(t *testing.T, extraHCL st func test_createAlias(t *testing.T, agent *TestAgent, chk *structs.CheckType, expectedResult string) func(r *retry.R) { t.Helper() - serviceNum := rand.Int() + serviceNum := mathrand.Int() srv := &structs.NodeService{ Service: fmt.Sprintf("serviceAlias-%d", serviceNum), Tags: []string{"tag1"}, diff --git a/agent/consul/auto_config_endpoint_test.go b/agent/consul/auto_config_endpoint_test.go index 1036044fabca..a56fdfb4de83 100644 --- a/agent/consul/auto_config_endpoint_test.go +++ b/agent/consul/auto_config_endpoint_test.go @@ -3,7 +3,7 @@ package consul import ( "bytes" "crypto" - crand "crypto/rand" + "crypto/rand" "crypto/x509" "encoding/base64" "encoding/pem" @@ -884,7 +884,7 @@ func TestAutoConfig_parseAutoConfigCSR(t *testing.T) { // customizations to allow for better unit testing. createCSR := func(tmpl *x509.CertificateRequest, privateKey crypto.Signer) (string, error) { connect.HackSANExtensionForCSR(tmpl) - bs, err := x509.CreateCertificateRequest(crand.Reader, tmpl, privateKey) + bs, err := x509.CreateCertificateRequest(rand.Reader, tmpl, privateKey) require.NoError(t, err) var csrBuf bytes.Buffer err = pem.Encode(&csrBuf, &pem.Block{Type: "CERTIFICATE REQUEST", Bytes: bs}) diff --git a/agent/consul/internal_endpoint_test.go b/agent/consul/internal_endpoint_test.go index 698fc5681820..b9379c05b20b 100644 --- a/agent/consul/internal_endpoint_test.go +++ b/agent/consul/internal_endpoint_test.go @@ -1,9 +1,9 @@ package consul import ( + "crypto/rand" "encoding/base64" "fmt" - "math/rand" "os" "strings" "testing" diff --git a/agent/consul/leader_peering_test.go b/agent/consul/leader_peering_test.go index b8d7b8cf3a1d..1635bfe2e154 100644 --- a/agent/consul/leader_peering_test.go +++ b/agent/consul/leader_peering_test.go @@ -292,7 +292,7 @@ func TestLeader_PeeringSync_FailsForTLSError(t *testing.T) { t.Run("server-name-validation", func(t *testing.T) { testLeader_PeeringSync_failsForTLSError(t, func(token *structs.PeeringToken) { token.ServerName = "wrong.name" - }, `transport: authentication handshake failed: x509: certificate is valid for server.dc1.consul, bob.server.dc1.consul, not wrong.name`) + }, `transport: authentication handshake failed: tls: failed to verify certificate: x509: certificate is valid for server.dc1.peering.11111111-2222-3333-4444-555555555555.consul, not wrong.name`) }) t.Run("bad-ca-roots", func(t *testing.T) { wrongRoot, err := ioutil.ReadFile("../../test/client_certs/rootca.crt") @@ -300,7 +300,7 @@ func TestLeader_PeeringSync_FailsForTLSError(t *testing.T) { testLeader_PeeringSync_failsForTLSError(t, func(token *structs.PeeringToken) { token.CA = []string{string(wrongRoot)} - }, `transport: authentication handshake failed: x509: certificate signed by unknown authority`) + }, `transport: authentication handshake failed: tls: failed to verify certificate: x509: certificate signed by unknown authority`) }) } diff --git a/agent/consul/state/acl_test.go b/agent/consul/state/acl_test.go index 9634bf52f105..b91707391d3e 100644 --- a/agent/consul/state/acl_test.go +++ b/agent/consul/state/acl_test.go @@ -13,7 +13,6 @@ import ( "github.com/hashicorp/consul/acl" "github.com/hashicorp/consul/agent/structs" - "github.com/hashicorp/consul/lib" "github.com/hashicorp/consul/proto/pbacl" ) @@ -3690,7 +3689,6 @@ func TestStateStore_ACLPolicies_Snapshot_Restore(t *testing.T) { } func TestTokenPoliciesIndex(t *testing.T) { - lib.SeedMathRand() idIndex := &memdb.IndexSchema{ Name: "id", diff --git a/agent/coordinate_endpoint_test.go b/agent/coordinate_endpoint_test.go index 331451641f3a..bef55e50c61d 100644 --- a/agent/coordinate_endpoint_test.go +++ b/agent/coordinate_endpoint_test.go @@ -39,9 +39,9 @@ func TestCoordinate_Disabled_Response(t *testing.T) { req, _ := http.NewRequest("PUT", "/should/not/care", nil) resp := httptest.NewRecorder() obj, err := tt(resp, req) - if err, ok := err.(HTTPError); ok { - if err.StatusCode != 401 { - t.Fatalf("expected status 401 but got %d", err.StatusCode) + if httpErr, ok := err.(HTTPError); ok { + if httpErr.StatusCode != 401 { + t.Fatalf("expected status 401 but got %d", httpErr.StatusCode) } } else { t.Fatalf("expected HTTP error but got %v", err) diff --git a/agent/prepared_query_endpoint_test.go b/agent/prepared_query_endpoint_test.go index 9cf805b88c3f..89578683ae88 100644 --- a/agent/prepared_query_endpoint_test.go +++ b/agent/prepared_query_endpoint_test.go @@ -12,9 +12,10 @@ import ( "github.com/hashicorp/consul/testrpc" + "github.com/stretchr/testify/require" + "github.com/hashicorp/consul/agent/structs" "github.com/hashicorp/consul/types" - "github.com/stretchr/testify/require" ) // MockPreparedQuery is a fake endpoint that we inject into the Consul server @@ -621,9 +622,9 @@ func TestPreparedQuery_Execute(t *testing.T) { req, _ := http.NewRequest("GET", "/v1/query/not-there/execute", body) resp := httptest.NewRecorder() _, err := a.srv.PreparedQuerySpecific(resp, req) - if err, ok := err.(HTTPError); ok { - if err.StatusCode != 404 { - t.Fatalf("expected status 404 but got %d", err.StatusCode) + if httpErr, ok := err.(HTTPError); ok { + if httpErr.StatusCode != 404 { + t.Fatalf("expected status 404 but got %d", httpErr.StatusCode) } } else { t.Fatalf("expected HTTP error but got %v", err) @@ -760,9 +761,9 @@ func TestPreparedQuery_Explain(t *testing.T) { req, _ := http.NewRequest("GET", "/v1/query/not-there/explain", body) resp := httptest.NewRecorder() _, err := a.srv.PreparedQuerySpecific(resp, req) - if err, ok := err.(HTTPError); ok { - if err.StatusCode != 404 { - t.Fatalf("expected status 404 but got %d", err.StatusCode) + if httpErr, ok := err.(HTTPError); ok { + if httpErr.StatusCode != 404 { + t.Fatalf("expected status 404 but got %d", httpErr.StatusCode) } } else { t.Fatalf("expected HTTP error but got %v", err) @@ -853,9 +854,9 @@ func TestPreparedQuery_Get(t *testing.T) { req, _ := http.NewRequest("GET", "/v1/query/f004177f-2c28-83b7-4229-eacc25fe55d1", body) resp := httptest.NewRecorder() _, err := a.srv.PreparedQuerySpecific(resp, req) - if err, ok := err.(HTTPError); ok { - if err.StatusCode != 404 { - t.Fatalf("expected status 404 but got %d", err.StatusCode) + if httpErr, ok := err.(HTTPError); ok { + if httpErr.StatusCode != 404 { + t.Fatalf("expected status 404 but got %d", httpErr.StatusCode) } } else { t.Fatalf("expected HTTP error but got %v", err) diff --git a/agent/testagent.go b/agent/testagent.go index 5701834b7cc8..ab0f35812d5c 100644 --- a/agent/testagent.go +++ b/agent/testagent.go @@ -6,7 +6,6 @@ import ( "crypto/x509" "fmt" "io" - "math/rand" "net" "net/http/httptest" "path/filepath" @@ -32,10 +31,6 @@ import ( "github.com/hashicorp/consul/tlsutil" ) -func init() { - rand.Seed(time.Now().UnixNano()) // seed random number generator -} - // TestAgent encapsulates an Agent with a default configuration and // startup procedure suitable for testing. It panics if there are errors // during creation or startup instead of returning errors. It manages a diff --git a/agent/txn_endpoint_test.go b/agent/txn_endpoint_test.go index f6f47b8fab59..2dc5287e3bdf 100644 --- a/agent/txn_endpoint_test.go +++ b/agent/txn_endpoint_test.go @@ -67,9 +67,9 @@ func TestTxnEndpoint_Bad_Size_Item(t *testing.T) { t.Fatalf("err: %v", err) } } else { - if err, ok := err.(HTTPError); ok { - if err.StatusCode != 413 { - t.Fatalf("expected 413 but got %d", err.StatusCode) + if httpErr, ok := err.(HTTPError); ok { + if httpErr.StatusCode != 413 { + t.Fatalf("expected 413 but got %d", httpErr.StatusCode) } } else { t.Fatalf("excected HTTP error but got %v", err) @@ -150,9 +150,9 @@ func TestTxnEndpoint_Bad_Size_Net(t *testing.T) { t.Fatalf("err: %v", err) } } else { - if err, ok := err.(HTTPError); ok { - if err.StatusCode != 413 { - t.Fatalf("expected 413 but got %d", err.StatusCode) + if httpErr, ok := err.(HTTPError); ok { + if httpErr.StatusCode != 413 { + t.Fatalf("expected 413 but got %d", httpErr.StatusCode) } } else { t.Fatalf("excected HTTP error but got %v", err) @@ -220,9 +220,9 @@ func TestTxnEndpoint_Bad_Size_Ops(t *testing.T) { resp := httptest.NewRecorder() _, err := a.srv.Txn(resp, req) - if err, ok := err.(HTTPError); ok { - if err.StatusCode != 413 { - t.Fatalf("expected 413 but got %d", err.StatusCode) + if httpErr, ok := err.(HTTPError); ok { + if httpErr.StatusCode != 413 { + t.Fatalf("expected 413 but got %d", httpErr.StatusCode) } } else { t.Fatalf("expected HTTP error but got %v", err) diff --git a/api/go.mod b/api/go.mod index 64093899a0c8..b6f312c8fbb7 100644 --- a/api/go.mod +++ b/api/go.mod @@ -1,6 +1,6 @@ module github.com/hashicorp/consul/api -go 1.12 +go 1.20 replace github.com/hashicorp/consul/sdk => ../sdk diff --git a/command/members/members_test.go b/command/members/members_test.go index cc4a21742aec..c9a2d42b77d6 100644 --- a/command/members/members_test.go +++ b/command/members/members_test.go @@ -13,7 +13,6 @@ import ( "github.com/hashicorp/consul/agent" consulapi "github.com/hashicorp/consul/api" - "github.com/hashicorp/consul/lib" ) // TODO(partitions): split these tests @@ -206,8 +205,6 @@ func zip(t *testing.T, k, v []string) map[string]string { } func TestSortByMemberNamePartitionAndSegment(t *testing.T) { - lib.SeedMathRand() - // For the test data we'll give them names that would sort them backwards // if we only sorted by name. newData := func() []*consulapi.AgentMember { diff --git a/lib/rand.go b/lib/rand.go deleted file mode 100644 index 22aa4f3544bb..000000000000 --- a/lib/rand.go +++ /dev/null @@ -1,34 +0,0 @@ -package lib - -import ( - crand "crypto/rand" - "math" - "math/big" - "math/rand" - "sync" - "time" -) - -var ( - once sync.Once - - // SeededSecurely is set to true if a cryptographically secure seed - // was used to initialize rand. When false, the start time is used - // as a seed. - SeededSecurely bool -) - -// SeedMathRand provides weak, but guaranteed seeding, which is better than -// running with Go's default seed of 1. A call to SeedMathRand() is expected -// to be called via init(), but never a second time. -func SeedMathRand() { - once.Do(func() { - n, err := crand.Int(crand.Reader, big.NewInt(math.MaxInt64)) - if err != nil { - rand.Seed(time.Now().UTC().UnixNano()) - return - } - rand.Seed(n.Int64()) - SeededSecurely = true - }) -} diff --git a/main.go b/main.go index e7b04e241fb5..35bb04281d6d 100644 --- a/main.go +++ b/main.go @@ -11,14 +11,9 @@ import ( "github.com/hashicorp/consul/command" "github.com/hashicorp/consul/command/cli" "github.com/hashicorp/consul/command/version" - "github.com/hashicorp/consul/lib" _ "github.com/hashicorp/consul/service_os" ) -func init() { - lib.SeedMathRand() -} - func main() { os.Exit(realMain()) } diff --git a/sdk/freeport/freeport.go b/sdk/freeport/freeport.go index 6eda1d4279b9..6c275fe86674 100644 --- a/sdk/freeport/freeport.go +++ b/sdk/freeport/freeport.go @@ -114,7 +114,6 @@ func initialize() { panic("freeport: block size too big or too many blocks requested") } - rand.Seed(time.Now().UnixNano()) firstPort, lockLn = alloc() condNotEmpty = sync.NewCond(&mu) diff --git a/sdk/go.mod b/sdk/go.mod index 18b289a0e8ba..6c7b5f88b8f6 100644 --- a/sdk/go.mod +++ b/sdk/go.mod @@ -1,6 +1,6 @@ module github.com/hashicorp/consul/sdk -go 1.12 +go 1.20 require ( github.com/fatih/color v1.9.0 // indirect diff --git a/tlsutil/config_test.go b/tlsutil/config_test.go index eda15aecfae1..d0c4318735a4 100644 --- a/tlsutil/config_test.go +++ b/tlsutil/config_test.go @@ -754,7 +754,7 @@ func TestConfigurator_outgoingWrapperALPN_serverHasNoNodeNameInSAN(t *testing.T) _, err = wrap("dc1", "bob", "foo", client) require.Error(t, err) - _, ok := err.(x509.HostnameError) + _, ok := err.(*tls.CertificateVerificationError) require.True(t, ok) client.Close()