OpenNHP/opennhp · error

failed to create AES-GCM

Error message

failed to create AES-GCM: %w

What it means

AeadFromKey wraps cipher.NewGCM(aesBlock) failure with this message. Go's cipher.NewGCM returns an error only if the block cipher's block size is not 16 bytes; a real aes.Block from crypto/aes always has a 16-byte block size, so this error is practically unreachable with the standard library and signals dependency corruption or a custom cipher.Block implementation. It is defensive wrapping for completeness.

Solutions

  1. Run 'go mod verify' and rebuild with an official Go toolchain
  2. Check for replace directives or vendored forks of crypto/cipher or crypto/aes
  3. Update Go to a current supported release and rerun go test ./nhp/core/...
  4. Log the wrapped error to capture the underlying NewGCM message
Defensive patterns

Strategy: try-catch

Validate before calling

block, err := aes.NewCipher(key[:])
if err == nil && block.BlockSize() != 16 {
    return fmt.Errorf("unexpected AES block size %d", block.BlockSize())
}

Try / catch

aead, err := core.AeadFromKey(core.GCM_AES256, &key)
if err != nil {
    return fmt.Errorf("GCM init failed: %w", err)
}

Prevention

When it happens

Trigger: cipher.NewGCM receiving a block whose BlockSize() != 16 — only possible if crypto/aes is replaced by a non-conforming implementation or the Go toolchain/dependency graph is corrupted.

Common situations: Vendored or forked Go crypto stacks, exotic build environments, or tampered dependencies. Normal OpenNHP operation (knock, ACK, DHP traffic encryption) will not hit it.

Understand the failure class

Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.

Related errors


AI-assisted analysis of OpenNHP/opennhp@6e04ca5ff0 (2026-09-07). Data as JSON: /api/errors/ba57fd50671ae4d8. Report an issue: GitHub.

Appendix: source

Thrown at nhp/core/crypto.go:160

		e = curve.NewECDH()

	case ECC_SM2:
		e = gmsm.NewECDH()
	}

	return e
}

func AeadFromKey(t GcmTypeEnum, key *[SymmetricKeySize]byte) (cipher.AEAD, error) {
	switch t {
	case GCM_AES256:
		aesBlock, err := aes.NewCipher(key[:])
		if err != nil {
			return nil, fmt.Errorf("failed to create AES cipher: %w", err)
		}
		aead, err := cipher.NewGCM(aesBlock)
		if err != nil {
			return nil, fmt.Errorf("failed to create AES-GCM: %w", err)
		}
		return aead, nil

	case GCM_SM4:
		sm4Block, err := sm4.NewCipher(key[:16])
		if err != nil {
			return nil, fmt.Errorf("failed to create SM4 cipher: %w", err)
		}
		aead, err := cipher.NewGCM(sm4Block)
		if err != nil {
			return nil, fmt.Errorf("failed to create SM4-GCM: %w", err)
		}
		return aead, nil

	case GCM_CHACHA20POLY1305:
		aead, err := chacha20poly1305.New(key[:])
		if err != nil {
			return nil, fmt.Errorf("failed to create ChaCha20-Poly1305: %w", err)

View on GitHub (pinned to 6e04ca5ff0)