kubernetes/kops · error

failed to assign prefix

Error message

failed to assign prefix: %w

What it means

RenderLocal calls EC2 AssignIpv6Addresses to delegate an /80 IPv6 prefix to the instance's primary network interface; if the EC2 API call fails, the underlying AWS SDK error is wrapped with this message. This usually means the ENI is not configured for prefix delegation.

Solutions

  1. Verify the subnet has an IPv6 CIDR associated (`aws ec2 describe-subnets`) and that prefix delegation is supported in that AZ.
  2. Ensure the instance IAM role permits ec2:AssignIpv6Addresses on the ENI.
  3. Check the wrapped SDK error for throttling (RequestLimitExceeded) and retry with backoff.
  4. Confirm the ENI is the instance's primary interface with device index 0 and IPv6 enabled.
Defensive patterns

Strategy: retry

Validate before calling

// pre-checks
subnets must have associated IPv6 CIDR
instance IAM role must allow ec2:AssignIpv6Addresses

Try / catch

var ae smithy.APIError
if errors.As(err, &ae) {
    if ae.ErrorCode() == "RequestLimitExceeded" || ae.Fault() == smithy.FaultServer {
        // retry with exponential backoff
    }
}

Prevention

When it happens

Trigger: Calling AssignIpv6Addresses with Ipv6PrefixCount=1 on a network interface whose subnet lacks an associated IPv6 CIDR, has no prefix delegation enabled, or where the API returns auth/throttling/permission errors.

Common situations: Subnet created without an IPv6 CIDR; instance metadata/IMDS unavailable so the wrong interface ID; IAM role missing ec2:AssignIpv6Addresses permission; EC2 API throttling during cluster bring-up.

Related errors


AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05). Data as JSON: /api/errors/f78d04a39e0a91d2. Report an issue: GitHub.

Appendix: source

Thrown at upup/pkg/fi/nodeup/nodetasks/prefix.go:103

func (_ *Prefix) RenderLocal(t *local.LocalTarget, a, e, changes *Prefix) error {
	ctx := context.TODO()
	mac, err := getInstanceMetadataFirstValue(ctx, "mac")
	if err != nil {
		return err
	}

	interfaceId, err := getInstanceMetadataFirstValue(ctx, path.Join("network/interfaces/macs/", mac, "/interface-id"))
	if err != nil {
		return err
	}

	response, err := t.Cloud.AssignIpv6Addresses(ctx, &ec2.AssignIpv6AddressesInput{
		Ipv6PrefixCount:    new(int32(1)),
		NetworkInterfaceId: new(interfaceId),
	})
	if err != nil {
		return fmt.Errorf("failed to assign prefix: %w", err)
	}
	klog.V(2).Infof("assigned prefix to primary network interface: %q", response.AssignedIpv6Prefixes[0])

	return nil
}

func getInstanceMetadataFirstValue(ctx context.Context, category string) (string, error) {
	values, err := getInstanceMetadataList(ctx, category)
	if err != nil {
		return "", err
	}
	if len(values) == 0 {
		return "", fmt.Errorf("failed to get %q from ec2 meta-data: not found", category)
	}

	return values[0], nil
}

View on GitHub (pinned to 4c8573c808)