golang/go · error

cipher: the nonce can't have zero length

Error message

cipher: the nonce can't have zero length

What it means

Returned by gcm.New when nonceSize <= 0. GCM requires a positive nonce length; the standard nonce is 12 bytes but the API allows other lengths (via a slower path), except zero. Surfaces through cipher.NewGCMWithNonceSize or cipher.NewGCM(..., WithNonceSize(n)).

Source

Thrown at src/crypto/internal/fips140/aes/gcm/gcm.go:36

	tagSize   int
	gcmPlatformData
}

func New(cipher *aes.Block, nonceSize, tagSize int) (*GCM, error) {
	// This function is outlined to let the allocation happen on the parent stack.
	return newGCM(&GCM{}, cipher, nonceSize, tagSize)
}

// newGCM is marked go:noinline to avoid it inlining into New, and making New
// too complex to inline itself.
//
//go:noinline
func newGCM(g *GCM, cipher *aes.Block, nonceSize, tagSize int) (*GCM, error) {
	if tagSize < gcmMinimumTagSize || tagSize > gcmBlockSize {
		return nil, errors.New("cipher: incorrect tag size given to GCM")
	}
	if nonceSize <= 0 {
		return nil, errors.New("cipher: the nonce can't have zero length")
	}
	if cipher.BlockSize() != gcmBlockSize {
		return nil, errors.New("cipher: NewGCM requires 128-bit block cipher")
	}
	g.cipher = *cipher
	g.nonceSize = nonceSize
	g.tagSize = tagSize
	initGCM(g)
	return g, nil
}

const (
	gcmBlockSize         = 16
	gcmTagSize           = 16
	gcmMinimumTagSize    = 12 // NIST SP 800-38D recommends tags with 12 or more bytes.
	gcmStandardNonceSize = 12
)

View on GitHub (pinned to b6b368adc5)

Solutions

  1. Use the standard 12-byte nonce unless you have a specific reason to change it.
  2. If omitted, omit the option entirely so gcmStandardNonceSize (12) applies.
  3. Validate nonceSize > 0 before constructing the AEAD.

Example fix

// before
aead, err := cipher.NewGCM(block, cipher.WithNonceSize(0))
// after
aead, err := cipher.NewGCM(block) // default 12-byte nonce
// or explicit:
aead, err := cipher.NewGCM(block, cipher.WithNonceSize(12))
Defensive patterns

Strategy: validation

Validate before calling

func validGCMNonceSize(n int) bool { return n > 0 }

if !validGCMNonceSize(nonceSize) { return errors.New("nonce size must be > 0") }
aead, err := cipher.NewGCM(block, cipher.WithNonceSize(nonceSize))

Type guard

// n/a: int parameter; guard with range check.

Try / catch

aead, err := cipher.NewGCM(block, cipher.WithNonceSize(nonceSize))
if err != nil { return fmt.Errorf("gcm init: %w", err) }

Prevention

When it happens

Trigger: Calling cipher.NewGCM(block, cipher.WithNonceSize(n)) or gcm.New(block, n, tagSize) with n <= 0.

Common situations: Passing nonceSize=0 from an uninitialized/config-derived value; computing nonce size from a length-of-empty slice; misreading the standard 12-byte default.

Related errors


AI-assisted analysis of golang/go@b6b368adc5 (2026-08-12). Data as JSON: /api/errors/2115756e001e8f75. Report an issue: GitHub.