AdguardTeam/AdGuardHome · error
login: expected length %d, got %d
Error message
login: expected length %d, got %d
What it means
bboltDecode validates that the trailing name bytes match the 2-byte big-endian length prefix; a mismatch means the record is internally inconsistent and cannot be safely decoded. Like error 61, it points to corrupted or foreign data in the sessions bucket.
Source
Thrown at internal/aghuser/sessionstorage.go:294
// bboltSessionNameLen is the length of the name field in the binary entry
// stored in bbolt.
bboltSessionNameLen = 2
)
// bboltDecode deserializes decodes a binary data into a session.
func bboltDecode(data []byte) (s *Session, err error) {
if len(data) < bboltSessionExpireLen+bboltSessionNameLen {
return nil, fmt.Errorf("length of the data is less than expected: got %d", len(data))
}
expireData := data[:bboltSessionExpireLen]
nameLenData := data[bboltSessionExpireLen : bboltSessionExpireLen+bboltSessionNameLen]
nameData := data[bboltSessionExpireLen+bboltSessionNameLen:]
nameLen := binary.BigEndian.Uint16(nameLenData)
if len(nameData) != int(nameLen) {
return nil, fmt.Errorf("login: expected length %d, got %d", nameLen, len(nameData))
}
expire := binary.BigEndian.Uint32(expireData)
return &Session{
Expire: time.Unix(int64(expire), 0),
UserLogin: Login(nameData),
}, nil
}
// bboltEncode serializes a session properties into a binary data.
func bboltEncode(s *Session) (data []byte) {
data = make([]byte, bboltSessionExpireLen+bboltSessionNameLen+len(s.UserLogin))
expireData := data[:bboltSessionExpireLen]
nameLenData := data[bboltSessionExpireLen : bboltSessionExpireLen+bboltSessionNameLen]
nameData := data[bboltSessionExpireLen+bboltSessionNameLen:]
View on GitHub (pinned to b41aefbe51)
Solutions
- Delete the sessions db file so invalid records are purged and users re-login
- Pin one AdGuard Home version (avoid downgrade after upgrade)
- Run bbolt integrity checks / restore backup
Defensive patterns
Strategy: fallback
Type guard
func sessionNameLenMatches(b []byte) bool {
if len(b) < 6 { return false }
return int(binary.BigEndian.Uint16(b[4:6])) == len(b)-6
} Try / catch
// treat as corrupt record: purge db, restart clean
if err != nil && strings.Contains(err.Error(), "login: expected length") { purgeSessionDB() } Prevention
- Pin versions consistently
- Use fsync-friendly local storage for the db
When it happens
Trigger: A bucket value where the declared login-name length does not equal the remaining bytes — truncated record, tampering, or an incompatible serialization version.
Common situations: Crash during a session write; manual editing of the db; format drift between versions.
Related errors
- length of the data is less than expected: got %d
- loading sessions: %w
- processing sessions: %w
- iterating over sessions: %w
- deleting sessions: %w
AI-assisted analysis of AdguardTeam/AdGuardHome@b41aefbe51 (2026-08-27).
Data as JSON: /api/errors/95622f624254ebbe.
Report an issue: GitHub.