diff --git a/.github/workflows/go.yml b/.github/workflows/go.yml index 24e1838..80c6b04 100644 --- a/.github/workflows/go.yml +++ b/.github/workflows/go.yml @@ -10,16 +10,13 @@ on: jobs: build: - name: Build ${{ matrix.go-version }} + name: Build runs-on: ubuntu-latest - strategy: - matrix: - go-version: [1.22.8, 1.23.2] steps: - - name: Set up Go ${{ matrix.go-version }} + - name: Set up Go uses: actions/setup-go@v5 with: - go-version: ${{ matrix.go-version }} + go-version: 1.24.3 - name: Check out code into the Go module directory uses: actions/checkout@v4 - name: Build and Lint @@ -27,48 +24,42 @@ jobs: go build ./... go vet -tests=false ./... # Specifically for examples without a corresponding identifier test: - name: Text ${{ matrix.os }} | ${{ matrix.go-version }} + name: Text ${{ matrix.os }} runs-on: ${{ matrix.os }} strategy: matrix: - go-version: [1.22.8, 1.23.2] os: [ubuntu-latest, windows-latest, macos-latest] steps: - - name: Set up Go ${{ matrix.go-version }} on ${{ matrix.os }} + - name: Set up Go uses: actions/setup-go@v5 with: - go-version: ${{ matrix.go-version }} + go-version: 1.24.3 - name: Check out code into the Go module directory uses: actions/checkout@v4 - name: Test on ${{ matrix.os }} run: | go test ./... - boringcrypto: + fips140: + name: 'Test FIPS 140' runs-on: ubuntu-latest - strategy: - matrix: - go-version: [1.22.8, 1.23.2] steps: - - name: Set up Go ${{ matrix.go-version }} + - name: Set up Go uses: actions/setup-go@v5 with: - go-version: ${{ matrix.go-version }} + go-version: 1.24.3 - name: Check out code into the Go module directory uses: actions/checkout@v4 - name: Test run: | - CGO_ENABLED=1 GOEXPERIMENT=boringcrypto go test ./... + GODEBUG=fips140=on go test ./... vulncheck: - name: Vulncheck ${{ matrix.go-version }} + name: Vulncheck runs-on: ubuntu-latest - strategy: - matrix: - go-version: [1.22.8, 1.23.2] steps: - name: Set up Go ${{ matrix.go-version }} uses: actions/setup-go@v5 with: - go-version: ${{ matrix.go-version }} + go-version: 1.24.3 - name: Check out code into the Go module directory uses: actions/checkout@v4 - name: Get govulncheck diff --git a/boring_test.go b/boring_test.go deleted file mode 100644 index f2ac4d0..0000000 --- a/boring_test.go +++ /dev/null @@ -1,34 +0,0 @@ -// Copyright (c) 2024 Andreas Auernhammer. All rights reserved. -// Use of this source code is governed by a license that can be -// found in the LICENSE file. - -//go:build boringcrypto - -package mtls_test - -import ( - "testing" - - "aead.dev/mtls" -) - -func TestBoringCrypto(t *testing.T) { - const Key = "k1:xZnpcYtPdVMNLBBRaUO5HPEoK_jVrcc3MWR8BshkjJw" - - if _, err := mtls.ParsePrivateKey(Key); err == nil { - t.Fatal("Parsed Ed25519 private key in FIPS mode successfully") - } - - if _, err := mtls.GenerateKeyEdDSA(nil); err == nil { - t.Fatal("Generated Ed25519 private key in FIPS mode successfully") - } - - var k mtls.EdDSAPrivateKey - if err := k.UnmarshalText([]byte(Key)); err == nil { - t.Fatal("Unmarshaled Ed25519 private key in FIPS mode successfully") - } - - if _, err := k.MarshalText(); err == nil { - t.Fatal("Marshaled Ed25519 private key in FIPS mode successfully") - } -} diff --git a/example_test.go b/example_test.go index 3f99077..a8675f5 100644 --- a/example_test.go +++ b/example_test.go @@ -247,10 +247,10 @@ func ExampleServer_VerifyPeerIdentity() { // Output: } -// ExampleClientServer shows how to send a GET request from a client to server +// Shows how to send a GET request from a client to server // over a mTLS connection. The client and server verify the identity of their // peers. -func ExampleClientServer() { +func Example() { // The client and server private key. Private keys should never be exposed! const ( ServerPrivateKey = "k2:RsxEXi8ebLIWI8BI9MJHGBqKa1keq67Ds8hrgetZV1M" // Only known to the server diff --git a/internal/boring/boring.go b/internal/boring/boring.go deleted file mode 100644 index 89f0279..0000000 --- a/internal/boring/boring.go +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright (c) 2024 Andreas Auernhammer. All rights reserved. -// Use of this source code is governed by a license that can be -// found in the LICENSE file. - -//go:build boringcrypto - -package boring - -const FIPS = true diff --git a/internal/boring/noboring.go b/internal/boring/noboring.go deleted file mode 100644 index 8554d9c..0000000 --- a/internal/boring/noboring.go +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright (c) 2024 Andreas Auernhammer. All rights reserved. -// Use of this source code is governed by a license that can be -// found in the LICENSE file. - -//go:build !boringcrypto - -package boring - -const FIPS = false diff --git a/key.go b/key.go index 9f2707d..75b52a4 100644 --- a/key.go +++ b/key.go @@ -25,8 +25,6 @@ import ( "strconv" "strings" "time" - - "aead.dev/mtls/internal/boring" ) // PrivateKey is private key for TLS and mutual TLS connections. @@ -55,9 +53,6 @@ func ParsePrivateKey(s string) (PrivateKey, error) { return nil, errors.New("mtls: invalid private key") case strings.HasPrefix(s, "k1:"): - if boring.FIPS { - return nil, errors.New("mtls: ed25519 not supported by FIPS module") - } var key EdDSAPrivateKey if err := key.UnmarshalText([]byte(s)); err != nil { return nil, err @@ -83,10 +78,6 @@ type EdDSAPrivateKey struct { // GenerateKeyEdDSA generates a new [EdDSAPrivateKey] using entropy // from random. If random is nil, [crypto/rand.Reader] will be used. func GenerateKeyEdDSA(random io.Reader) (*EdDSAPrivateKey, error) { - if boring.FIPS { - return nil, errors.New("mtls: ed25519 not supported by FIPS module") - } - if random == nil { random = rand.Reader } @@ -107,9 +98,6 @@ func GenerateKeyEdDSA(random io.Reader) (*EdDSAPrivateKey, error) { // Private returns the EdDSA private key. func (pk *EdDSAPrivateKey) Private() crypto.PrivateKey { - if boring.FIPS { - panic("mtls: ed25519 not supported by FIPS module") - } priv := make(ed25519.PrivateKey, ed25519.PrivateKeySize) copy(priv, pk.priv) return priv @@ -117,17 +105,11 @@ func (pk *EdDSAPrivateKey) Private() crypto.PrivateKey { // Public returns the EdDSA public key. func (pk *EdDSAPrivateKey) Public() crypto.PublicKey { - if boring.FIPS { - panic("mtls: ed25519 not supported by FIPS module") - } return pk.priv.Public() } // Identity returns the identity of the EdDSA public key. func (pk *EdDSAPrivateKey) Identity() Identity { - if boring.FIPS { - panic("mtls: ed25519 not supported by FIPS module") - } return pk.identity } @@ -135,10 +117,6 @@ func (pk *EdDSAPrivateKey) Identity() Identity { // // It returns output equivalent to [EdDSAPrivateKey.String] func (pk *EdDSAPrivateKey) MarshalText() ([]byte, error) { - if boring.FIPS { - return nil, errors.New("mtls: ed25519 not supported by FIPS module") - } - var text [46]byte b := append(text[:0], "k1:"...) b = base64.RawURLEncoding.AppendEncode(b, pk.priv[:ed25519.SeedSize]) @@ -147,10 +125,6 @@ func (pk *EdDSAPrivateKey) MarshalText() ([]byte, error) { // UnmarshalText parses a private key textual representation. func (pk *EdDSAPrivateKey) UnmarshalText(text []byte) error { - if boring.FIPS { - return errors.New("mtls: ed25519 not supported by FIPS module") - } - if !bytes.HasPrefix(text, []byte("k1:")) { return errors.New("mtls: invalid EdDSA private key") } @@ -181,10 +155,6 @@ func (pk *EdDSAPrivateKey) UnmarshalText(text []byte) error { // // Its output is equivalent to [EdDSAPrivateKey.MarshalText] func (pk *EdDSAPrivateKey) String() string { - if boring.FIPS { - panic("mtls: ed25519 not supported by FIPS module") - } - return "k1:" + base64.RawURLEncoding.EncodeToString(pk.priv[:ed25519.SeedSize]) } diff --git a/key_test.go b/key_test.go index 2ef2146..f73dab2 100644 --- a/key_test.go +++ b/key_test.go @@ -15,15 +15,11 @@ import ( "testing" "aead.dev/mtls" - "aead.dev/mtls/internal/boring" ) // TestGenerateKeyEdDSA tests whether generated EdDSA private keys // are equal to their parsed textual representation func TestGenerateKeyEdDSA(t *testing.T) { - if boring.FIPS { - t.Skip("Ed25519 is not available in FIPS mode") - } t.Parallel() key, err := mtls.GenerateKeyEdDSA(rand.Reader) @@ -73,10 +69,6 @@ func TestGenerateKeyECDSA(t *testing.T) { // identity of the corresponding private key. func TestPrivateKey_Identity(t *testing.T) { for _, test := range privateKeyIdentityTests { - if boring.FIPS && test.SkipFIPS { - continue - } - key, err := mtls.ParsePrivateKey(test.PrivateKey) if err != nil { t.Fatalf("failed to parse private key %s: %v", test.PrivateKey, err) @@ -107,12 +99,10 @@ func TestPrivateKey_Identity(t *testing.T) { var privateKeyIdentityTests = []struct { Filename string PrivateKey string - SkipFIPS bool // Skip test in FIPS mode }{ { Filename: "./testdata/certs/ed25519.crt", PrivateKey: "k1:xZnpcYtPdVMNLBBRaUO5HPEoK_jVrcc3MWR8BshkjJw", - SkipFIPS: boring.FIPS, }, { Filename: "./testdata/certs/p-256.crt",