redis/redis
robj
The Redis value wrapper. Every value in the keyspace is a robj.
Source layout
| File | Role |
|---|---|
src/object.c |
The implementation (~71 KB). Constructors, destructors, encoding conversions, refcounting, MEMORY USAGE, OBJECT * commands. |
src/object.h |
Public type definitions. |
Layout
typedef struct redisObject {
unsigned type:4; /* OBJ_STRING / OBJ_LIST / OBJ_SET / OBJ_ZSET / OBJ_HASH / OBJ_STREAM */
unsigned encoding:4; /* OBJ_ENCODING_* */
unsigned lru:LRU_BITS; /* 24 bits */
int refcount;
void *ptr;
} robj;16 bytes on 64-bit platforms (4 bytes flags + 4 refcount + 8 ptr). The lru field packs either an LRU clock (24 bits) or an 8-bit LFU counter + 16-bit access timestamp depending on maxmemory-policy.
Type and encoding constants
/* Types */
#define OBJ_STRING 0
#define OBJ_LIST 1
#define OBJ_SET 2
#define OBJ_ZSET 3
#define OBJ_HASH 4
#define OBJ_MODULE 5
#define OBJ_STREAM 6
#define OBJ_TYPE_MAX 7
/* Encodings (selection) */
#define OBJ_ENCODING_RAW 0
#define OBJ_ENCODING_INT 1
#define OBJ_ENCODING_HT 2
#define OBJ_ENCODING_ZIPMAP 3 /* deprecated */
#define OBJ_ENCODING_LINKEDLIST 4 /* deprecated */
#define OBJ_ENCODING_ZIPLIST 5 /* deprecated for new objects, kept for RDB load */
#define OBJ_ENCODING_INTSET 6
#define OBJ_ENCODING_SKIPLIST 7
#define OBJ_ENCODING_EMBSTR 8
#define OBJ_ENCODING_QUICKLIST 9
#define OBJ_ENCODING_STREAM 10
#define OBJ_ENCODING_LISTPACK 11
#define OBJ_ENCODING_LISTPACK_EX 12
#define OBJ_ENCODING_LISTPACK_HFE 13Refcounting
incrRefCount(o) and decrRefCount(o) adjust the count. When it drops to zero, the type-specific freeXxxObject runs. There is also decrRefCountVoid(void *) for dict-destructor compatibility.
A few robjs are shared — they have a sentinel refcount (OBJ_SHARED_REFCOUNT) and are never freed. The set is precomputed in server.shared:
- Pre-built integer objects for 0..9999 (configurable via
OBJ_SHARED_INTEGERS). - Common error replies (
shared.wrongtypeerr,shared.noautherr,shared.bgsaveerr, …). - Common simple strings (
shared.ok,shared.crlf,shared.czero,shared.cone,shared.emptybulk, …). - The
select 0..15reply objects.
Sharing is critical for INCR/DECR and other counter workloads — each operation often returns a small integer that is already pre-allocated.
Encoding conversion
Several types adaptively switch encoding:
- A string created from
INCRstarts asOBJ_ENCODING_INT. IfAPPENDmakes it longer than 20 bytes (max integer string), it converts toEMBSTRorRAW. - A list starts as
OBJ_ENCODING_LISTPACK. When entry count or per-entry size exceeds the configured threshold, it converts toQUICKLIST. - A set starts as
INTSET(if all integers and small). On insertion of a non-integer or growth pastset-max-intset-entries, it converts toLISTPACK. On further growth or large element insertion, it converts toHT. - Hashes and sorted sets follow the same listpack→HT/SKIPLIST pattern.
The conversion functions live in the type files (e.g. setTypeConvert in src/t_set.c). They are invariant-preserving but not reversible — once an HT always an HT (no auto-shrink to listpack on delete).
OBJECT command
OBJECT REFCOUNT <key>, OBJECT ENCODING <key>, OBJECT IDLETIME <key>, OBJECT FREQ <key> expose the relevant fields. OBJECT HELP lists the subcommands. Implementation: objectCommand in src/object.c.
MEMORY USAGE
MEMORY USAGE <key> [SAMPLES n] walks an object and tallies bytes. The sampling parameter applies to types whose size is data-dependent (e.g. a hash with millions of fields — sampling N fields gives a fast estimate). The implementation is objectComputeSize in src/object.c.
Allocation patterns
| Path | Allocation |
|---|---|
createObject(type, ptr) |
One alloc for the robj. The data is at ptr. |
createEmbeddedStringObject(buf, len) |
One alloc for the robj + co-located SDS. |
createRawStringObject(buf, len) |
Two allocs: one for the robj, one for the SDS. |
createListObject(), createListPackObject(), etc. |
Type-specific. |
Decisions about which constructor to call live in tryObjectEncoding (call this once an object has its final value to enforce the most compact encoding).
Where to start modifying
- Add an encoding —
OBJ_ENCODING_*enum, conversion helper, RDB save/load opcodes, AOF rewrite, persistence tests. - Tweak shared objects —
createSharedObjectsinsrc/server.cand theOBJ_SHARED_*constants insrc/object.h. - Improve
MEMORY USAGE—objectComputeSize. Add a case for the new encoding.
Related pages
- SDS, Listpack & quicklist, Dict, Intset, Rax, Stream radix — the underlying storage primitives.
- Memory management — eviction, lazyfree, defrag.
Built by Factory AutoWiki from public repository content. It is a generated preview for codebase exploration, not source-maintained documentation.