ramsey/uuid · error · DceSecurityException
Local identifier out of bounds; it must be a value between 0
Error message
Local identifier out of bounds; it must be a value between 0 and 4294967295
What it means
When generating a DCE Security (version 2) UUID, a negative IntegerObject local identifier is rejected with DceSecurityException because the field is an unsigned 32-bit value (0..4294967295). The check runs before any identifier auto-derivation.
Source
Thrown at src/Generator/DceSecurityGenerator.php:73
public function __construct(
private NumberConverterInterface $numberConverter,
private TimeGeneratorInterface $timeGenerator,
private DceSecurityProviderInterface $dceSecurityProvider,
) {
}
public function generate(
int $localDomain,
?IntegerObject $localIdentifier = null,
?Hexadecimal $node = null,
?int $clockSeq = null,
): string {
if (!in_array($localDomain, self::DOMAINS)) {
throw new DceSecurityException('Local domain must be a valid DCE Security domain');
}
if ($localIdentifier && $localIdentifier->isNegative()) {
throw new DceSecurityException(
'Local identifier out of bounds; it must be a value between 0 and 4294967295',
);
}
if ($clockSeq > self::CLOCK_SEQ_HIGH || $clockSeq < self::CLOCK_SEQ_LOW) {
throw new DceSecurityException('Clock sequence out of bounds; it must be a value between 0 and 63');
}
switch ($localDomain) {
case Uuid::DCE_DOMAIN_ORG:
if ($localIdentifier === null) {
throw new DceSecurityException('A local identifier must be provided for the org domain');
}
break;
case Uuid::DCE_DOMAIN_PERSON:
if ($localIdentifier === null) {
$localIdentifier = $this->dceSecurityProvider->getUid();View on GitHub (pinned to da5b521600)
Solutions
- Pass a non-negative IntegerObject (or null to auto-derive uid/gid for person/group domains).
- Handle -1 sentinels at the source: treat them as 'unknown' and pass null instead.
- Clamp/mask upstream values to the 0..4294967295 range before constructing the Integer.
Example fix
// before $uuid = Uuid::uuid2(Uuid::DCE_DOMAIN_PERSON, new Integer($uid)); // $uid === -1 // after $identifier = $uid >= 0 ? new Integer($uid) : null; $uuid = Uuid::uuid2(Uuid::DCE_DOMAIN_PERSON, $identifier);
Defensive patterns
Strategy: validation
Validate before calling
if ($identifier !== null && ($identifier->isNegative() || $identifier->compareTo(new Integer(4294967295)) > 0)) {
throw new InvalidArgumentException('local identifier must be 0..4294967295');
}
$uuid = Uuid::uuid2($domain, $identifier); Type guard
function isValidDceIdentifier(\Ramsey\Uuid\Type\Integer $id): bool
{
return !$id->isNegative() && $id->compareTo(new \Ramsey\Uuid\Type\Integer(4294967295)) <= 0;
} Try / catch
try {
$uuid = Uuid::uuid2($domain, new Integer($uid));
} catch (\Ramsey\Uuid\Exception\DceSecurityException $e) {
// treat as unknown identity
$uuid = Uuid::uuid2($domain);
} Prevention
- Translate -1/never-set sentinels into null before building the Integer.
- Check isNegative() on IntegerObject values coming from external systems.
- Pass null for person/group to auto-derive uid/gid when the real id is unknown.
When it happens
Trigger: Uuid::uuid2(Uuid::DCE_DOMAIN_PERSON, new Integer(-1)); passing a sentinel negative value; a system call that returns -1 on failure and is wrapped unchecked into Integer.
Common situations: Using -1 as an 'unknown id' sentinel; error returns from posix/external systems fed straight into the generator; IDs arriving as signed values from another platform.
Related errors
- Clock sequence out of bounds; it must be a value between 0 a
- Local domain must be a valid DCE Security domain
- A local identifier must be provided for the org domain
- Unable to get a user identifier using the system DCE Securit
- Unable to get a group identifier using the system DCE Securi
AI-assisted analysis of ramsey/uuid@da5b521600 (2026-08-21).
Data as JSON: /api/errors/2c966fdac91ef35c.
Report an issue: GitHub.