containerd/containerd · error

user namespace configuration: %w

Error message

user namespace configuration: %w

What it means

This error wraps any failure from parseUsernsIDs while building snapshotter options for a pod sandbox with user namespace (userns) options. The library throws it because invalid or malformed user/group ID mappings in the pod's userns configuration make it impossible to construct correct snapshotter remap labels, and proceeding would produce a sandbox with wrong file ownership. It is a pre-flight validation failure of the user namespace configuration, not a runtime container failure.

Source

Thrown at internal/cri/server/podsandbox/helpers_linux.go:387

			return nil, nil, fmt.Errorf("can't use user namespace mode %q without UID and GID mappings", mode)
		}
	default:
		return nil, nil, fmt.Errorf("unsupported user namespace mode: %q", mode)
	}

	return uids, gids, nil
}

func snapshotterRemapOpts(nsOpts *runtime.NamespaceOption) ([]snapshots.Opt, error) {
	snapshotOpt := []snapshots.Opt{}
	usernsOpts := nsOpts.GetUsernsOptions()
	if usernsOpts == nil {
		return snapshotOpt, nil
	}

	uids, gids, err := parseUsernsIDs(usernsOpts)
	if err != nil {
		return nil, fmt.Errorf("user namespace configuration: %w", err)
	}

	if usernsOpts.GetMode() == runtime.NamespaceMode_POD {
		snapshotOpt = append(snapshotOpt, containerd.WithRemapperLabels(0, uids[0].HostID, 0, gids[0].HostID, uids[0].Size))
	}
	return snapshotOpt, nil
}

View on GitHub (pinned to 4246446a2b)

Solutions

  1. Fix the pod spec's userNamespace uidMappings/gidMappings so each entry has valid, non-zero size and in-range hostID/containerID integers
  2. Verify the CRI runtime (containerd + snapshotter) supports user namespace remapping and the configured snapshotter supports remap labels
  3. Check kubelet feature gates/config for user namespaces are consistent with the runtime version
  4. Inspect the wrapped error (%w) from parseUsernsIDs for the exact mapping entry that failed

Example fix

// before: pod spec with zero-size mapping
// uidMappings: [{hostID: 0, containerID: 0, size: 0}]
// after: valid mapping
// uidMappings: [{hostID: 165536, containerID: 0, size: 65536}]
Defensive patterns

Strategy: validation

Validate before calling

// validate userns mappings before submitting pod spec
func validUserns(u *runtime.UserNamespaceOptions) bool {
  if u == nil { return true }
  uids, gids := u.GetUids(), u.GetGids()
  if u.GetMode() == runtime.NamespaceMode_POD && (len(uids) == 0 || len(gids) == 0) { return false }
  for _, m := range append(uids, gids...) {
    if m.GetSize() <= 0 || m.GetHostID() < 0 || m.GetContainerID() < 0 { return false }
  }
  return true
}

Prevention

When it happens

Trigger: A pod sandbox is created with UserNamespace options set (usernsOpts != nil) and parseUsernsIDs fails - e.g. the pod spec's securityContext userNamespace mode is POD/TABULAR but uids/gids mappings are empty, have size 0, non-integer hostID/containerID values, or invalid bounds.

Common situations: Kubelet passes a pod spec with userNamespaces configured but malformed uidMappings/gidMappings; cluster upgraded to userns support but CRI plugin config or runtime lacks matching support; user manually crafts a CRI PodSandboxConfig with empty or zero-size ID ranges.

Related errors


AI-assisted analysis of containerd/containerd@4246446a2b (2026-09-02). Data as JSON: /api/errors/30b37f0d3e7dc8b0. Report an issue: GitHub.