Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 29 additions & 0 deletions cachedb/cachedb.h
Original file line number Diff line number Diff line change
Expand Up @@ -162,7 +162,36 @@ typedef struct cachedb_funcs_t {
*/
int (*is_replicated) (cachedb_con *con);


int capability;

/**
* OPTIONAL, advertised by CACHEDB_CAP_GET_BUF. Reads a value into a
* caller-owned buffer, so a hot read path need not allocate: it is
* get() without the pkg_malloc the caller would then have to free.
*
* @buf must be memory private to the calling process (its own stack or
* pkg). A backend may write into it speculatively and then abandon the
* attempt, so on ANY outcome other than a hit its contents are
* undefined - never a stale previous value to fall back on. The value
* is not NUL-terminated.
*
* Return values:
* -3: @buf is too small; *vlen is 0 and *needed holds the size that
* would be required (the caller may then fall back to get())
* -2: key does not exist, or has expired
* -1: internal error, or a malformed request (NULL @buf, or @buflen
* below the backend's documented minimum)
* 0: found; *vlen bytes were written to @buf, always <= @buflen
*
* *vlen and *needed are zeroed before anything else is done, so a
* caller that ignores the return code reads a zero length rather than
* an uninitialised one. @needed may be NULL. NOTE this differs from
* get(), which signals a hit with a positive value at the script
* boundary - a hit here is 0.
*/
int (*get_buf) (cachedb_con *con, str *attr, char *buf,
unsigned int buflen, unsigned int *vlen, unsigned int *needed);
} cachedb_funcs;

typedef struct cachedb_engines {
Expand Down
23 changes: 23 additions & 0 deletions cachedb/cachedb_cap.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,31 @@ typedef enum {
CACHEDB_CAP_MAP_REMOVE = 1<<13,
CACHEDB_CAP_MAP =
(CACHEDB_CAP_MAP_GET|CACHEDB_CAP_MAP_SET|CACHEDB_CAP_MAP_REMOVE),

/* backend implements get_buf() - an allocation-free read into a
* caller-owned buffer. Optional: every backend still provides get() */
CACHEDB_CAP_GET_BUF = 1<<14,
} cachedb_cap;

/*
* Preprocessor-visible companion to CACHEDB_CAP_GET_BUF. A consumer cannot test
* for the endpoint at runtime alone: get_buf is a struct member, so referencing it
* fails to compile against a core that predates it, and the capability above is an
* enum constant the preprocessor cannot see. This lets a module compile against
* either core and pick the allocation-free path up automatically:
*
* #ifdef CACHEDB_HAVE_GET_BUF
* if (cdbf.get_buf && CACHEDB_CAPABILITY(&cdbf, CACHEDB_CAP_GET_BUF))
* ... use it ...
* else
* #endif
* ... use get() ...
*
* The runtime half stays necessary: a core may provide the endpoint while the
* configured backend does not implement it.
*/
#define CACHEDB_HAVE_GET_BUF 1

#define CACHEDB_CAPABILITY(cdbf,cpv) (((cdbf)->capability & (cpv)) == (cpv))

static inline int check_cachedb_api(cachedb_engine *cde)
Expand Down
18 changes: 18 additions & 0 deletions modules/cachedb_perf/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
# cachedb_perf module
#
# WARNING: do not run this directly, it should be run by the master Makefile

include ../../Makefile.defs
auto_gen=
NAME=cachedb_perf.so

# The clusterer_controller pull transport is compiled only when that module is
# part of this build - the top-level Makefile exports CLUSTERER_CTRL_SUPPORT=1
# in that case (the clusterer module keys off the same hook). Without it,
# pulls and syncs use the clusterer module's bin links only, and an explicit
# pull_transport=clctr warns and degrades to bin.
ifeq ($(CLUSTERER_CTRL_SUPPORT),1)
DEFS+= -DCLUSTERER_CTRL_SUPPORT
endif

include ../../Makefile.modules
Loading