mirror of
https://github.com/libretro/RetroArch
synced 2025-04-16 08:43:10 +00:00
(LibretroDB) Update
This commit is contained in:
parent
fb5384feab
commit
fc82bd4d9d
@ -173,7 +173,7 @@ OBJ += frontend/frontend.o \
|
|||||||
|
|
||||||
ifeq ($(HAVE_LIBRETRODB), 1)
|
ifeq ($(HAVE_LIBRETRODB), 1)
|
||||||
OBJ += libretrodb/bintree.o \
|
OBJ += libretrodb/bintree.o \
|
||||||
libretrodb/rarchdb.o \
|
libretrodb/libretrodb.o \
|
||||||
libretrodb/query.o \
|
libretrodb/query.o \
|
||||||
libretrodb/rmsgpack.o \
|
libretrodb/rmsgpack.o \
|
||||||
libretrodb/rmsgpack_dom.o
|
libretrodb/rmsgpack_dom.o
|
||||||
|
@ -810,7 +810,7 @@ XML
|
|||||||
============================================================ */
|
============================================================ */
|
||||||
#ifdef HAVE_LIBRETRODB
|
#ifdef HAVE_LIBRETRODB
|
||||||
#include "../libretrodb/bintree.c"
|
#include "../libretrodb/bintree.c"
|
||||||
#include "../libretrodb/rarchdb.c"
|
#include "../libretrodb/libretrodb.c"
|
||||||
#include "../libretrodb/rmsgpack.c"
|
#include "../libretrodb/rmsgpack.c"
|
||||||
#include "../libretrodb/rmsgpack_dom.c"
|
#include "../libretrodb/rmsgpack_dom.c"
|
||||||
#include "../libretrodb/query.c"
|
#include "../libretrodb/query.c"
|
||||||
|
@ -4,7 +4,7 @@ INCFLAGS = -I. -I../libretro-sdk/include
|
|||||||
LUA_CONVERTER_OBJ = rmsgpack.o \
|
LUA_CONVERTER_OBJ = rmsgpack.o \
|
||||||
rmsgpack_dom.o \
|
rmsgpack_dom.o \
|
||||||
lua_common.o \
|
lua_common.o \
|
||||||
rarchdb.o \
|
libretrodb.o \
|
||||||
bintree.o \
|
bintree.o \
|
||||||
query.o \
|
query.o \
|
||||||
lua_converter.o \
|
lua_converter.o \
|
||||||
@ -13,10 +13,10 @@ LUA_CONVERTER_OBJ = rmsgpack.o \
|
|||||||
|
|
||||||
RARCHDB_TOOL_OBJ = rmsgpack.o \
|
RARCHDB_TOOL_OBJ = rmsgpack.o \
|
||||||
rmsgpack_dom.o \
|
rmsgpack_dom.o \
|
||||||
rarchdb_tool.o \
|
libretrodb_tool.o \
|
||||||
bintree.o \
|
bintree.o \
|
||||||
query.o \
|
query.o \
|
||||||
rarchdb.o \
|
libretrodb.o \
|
||||||
compat_fnmatch.c \
|
compat_fnmatch.c \
|
||||||
$(NULL)
|
$(NULL)
|
||||||
|
|
||||||
@ -24,7 +24,7 @@ TESTLIB_C = testlib.c \
|
|||||||
lua_common.c \
|
lua_common.c \
|
||||||
query.c \
|
query.c \
|
||||||
compat_fnmatch.c \
|
compat_fnmatch.c \
|
||||||
rarchdb.c \
|
libretrodb.c \
|
||||||
bintree.c \
|
bintree.c \
|
||||||
rmsgpack.c \
|
rmsgpack.c \
|
||||||
rmsgpack_dom.c \
|
rmsgpack_dom.c \
|
||||||
@ -35,7 +35,7 @@ TESTLIB_FLAGS = ${CFLAGS} ${LUA_FLAGS} -shared -fpic
|
|||||||
|
|
||||||
.PHONY: all clean check
|
.PHONY: all clean check
|
||||||
|
|
||||||
all: rmsgpack_test rarchdb_tool lua_converter
|
all: rmsgpack_test libretrodb_tool lua_converter
|
||||||
|
|
||||||
%.o: %.c
|
%.o: %.c
|
||||||
${CC} $(INCFLAGS) $< -c ${CFLAGS} -o $@
|
${CC} $(INCFLAGS) $< -c ${CFLAGS} -o $@
|
||||||
@ -43,7 +43,7 @@ all: rmsgpack_test rarchdb_tool lua_converter
|
|||||||
lua_converter: ${LUA_CONVERTER_OBJ}
|
lua_converter: ${LUA_CONVERTER_OBJ}
|
||||||
${CC} $(INCFLAGS) ${LUA_CONVERTER_OBJ} ${LUA_FLAGS} -o $@
|
${CC} $(INCFLAGS) ${LUA_CONVERTER_OBJ} ${LUA_FLAGS} -o $@
|
||||||
|
|
||||||
rarchdb_tool: ${RARCHDB_TOOL_OBJ}
|
libretrodb_tool: ${RARCHDB_TOOL_OBJ}
|
||||||
${CC} $(INCFLAGS) ${RARCHDB_TOOL_OBJ} -o $@
|
${CC} $(INCFLAGS) ${RARCHDB_TOOL_OBJ} -o $@
|
||||||
|
|
||||||
rmsgpack_test:
|
rmsgpack_test:
|
||||||
@ -56,4 +56,4 @@ check: testlib.so tests.lua
|
|||||||
lua ./tests.lua
|
lua ./tests.lua
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
rm -rf *.o rmsgpack_test lua_converter rarchdb_tool testlib.so
|
rm -rf *.o rmsgpack_test lua_converter libretrodb_tool testlib.so
|
||||||
|
@ -1,13 +1,13 @@
|
|||||||
# rarchdb
|
# libretrodb
|
||||||
A small read only database
|
A small read only database
|
||||||
Mainly to be used by retroarch
|
Mainly to be used by retroarch
|
||||||
|
|
||||||
# Usage
|
# Usage
|
||||||
Files specified later in the chain **will override** earlier ones if the same key exists multiple times.
|
Files specified later in the chain **will override** earlier ones if the same key exists multiple times.
|
||||||
|
|
||||||
To list out the content of a db `rarchdb_tool <db file> list`
|
To list out the content of a db `libretrodb_tool <db file> list`
|
||||||
To create an index `rarchdb_tool <db file> create-index <index name> <field name>`
|
To create an index `libretrodb_tool <db file> create-index <index name> <field name>`
|
||||||
To find an entry with an index `rarchdb_tool <db file> find <index name> <value>`
|
To find an entry with an index `libretrodb_tool <db file> find <index name> <value>`
|
||||||
|
|
||||||
# lua converters
|
# lua converters
|
||||||
In order to write you own converter you must have a lua file that implements the following functions:
|
In order to write you own converter you must have a lua file that implements the following functions:
|
||||||
@ -54,15 +54,15 @@ dat_converter snes.rdb rom.crc snes1.dat snes2.dat
|
|||||||
~~~
|
~~~
|
||||||
|
|
||||||
# Query examples
|
# Query examples
|
||||||
Some examples of queries you can use with rarchdbtool:
|
Some examples of queries you can use with libretrodbtool:
|
||||||
|
|
||||||
1) Glob pattern matching
|
1) Glob pattern matching
|
||||||
Usecase : Search for all games starting with 'Street Fighter' in the 'name' field (glob pattern matching)
|
Usecase : Search for all games starting with 'Street Fighter' in the 'name' field (glob pattern matching)
|
||||||
|
|
||||||
`rarchdb_tool <db file> find "{'name':glob('Street Fighter*')}"`
|
`libretrodb_tool <db file> find "{'name':glob('Street Fighter*')}"`
|
||||||
|
|
||||||
2) Combined number matching query
|
2) Combined number matching query
|
||||||
Usecase: Search for all games released on October 1995.
|
Usecase: Search for all games released on October 1995.
|
||||||
|
|
||||||
`rarchdb_tool <db file> find "{'releasemonth':10,'releaseyear':1995}"`
|
`libretrodb_tool <db file> find "{'releasemonth':10,'releaseyear':1995}"`
|
||||||
|
|
||||||
|
291
libretrodb/dat_converter.c
Normal file
291
libretrodb/dat_converter.c
Normal file
@ -0,0 +1,291 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <sys/stat.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <errno.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
#include "rarchdb.h"
|
||||||
|
#include "db_parser.h"
|
||||||
|
|
||||||
|
#define MAX_TOKEN 256
|
||||||
|
|
||||||
|
static char *strndup_(const char *s, size_t n)
|
||||||
|
{
|
||||||
|
char* buff = calloc(n, sizeof(char));
|
||||||
|
|
||||||
|
if (!buff)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
strncpy(buff, s, n);
|
||||||
|
return buff;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct rmsgpack_dom_value *get_map_value(const struct rmsgpack_dom_value *m, char* key)
|
||||||
|
{
|
||||||
|
struct rmsgpack_dom_value v;
|
||||||
|
|
||||||
|
v.type = RDT_STRING;
|
||||||
|
v.string.len = strlen(key);
|
||||||
|
v.string.buff = key;
|
||||||
|
return rmsgpack_dom_value_map_value(m, &v);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int load_string(int fd, struct rmsgpack_dom_value *out)
|
||||||
|
{
|
||||||
|
char tok[MAX_TOKEN];
|
||||||
|
ssize_t tok_size;
|
||||||
|
|
||||||
|
if ((tok_size = get_token(fd, tok, MAX_TOKEN)) < 0)
|
||||||
|
return tok_size;
|
||||||
|
|
||||||
|
out->type = RDT_STRING;
|
||||||
|
out->string.len = tok_size;
|
||||||
|
out->string.buff = strndup_(tok, tok_size);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int load_uint(int fd, struct rmsgpack_dom_value *out)
|
||||||
|
{
|
||||||
|
char tok[MAX_TOKEN], *c;
|
||||||
|
ssize_t tok_size;
|
||||||
|
uint64_t value = 0;
|
||||||
|
|
||||||
|
if ((tok_size = get_token(fd, tok, MAX_TOKEN)) < 0)
|
||||||
|
return tok_size;
|
||||||
|
|
||||||
|
for (c = tok; c < tok + tok_size; c++)
|
||||||
|
{
|
||||||
|
value *= 10;
|
||||||
|
value += *c - '0';
|
||||||
|
}
|
||||||
|
|
||||||
|
out->type = RDT_UINT;
|
||||||
|
out->uint_ = value;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int load_bin(int fd, struct rmsgpack_dom_value *out)
|
||||||
|
{
|
||||||
|
char tok[MAX_TOKEN];
|
||||||
|
ssize_t tok_size;
|
||||||
|
uint8_t h;
|
||||||
|
uint8_t l;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
if ((tok_size = get_token(fd, tok, MAX_TOKEN)) < 0)
|
||||||
|
return tok_size;
|
||||||
|
|
||||||
|
out->type = RDT_BINARY;
|
||||||
|
out->binary.len = tok_size / 2;
|
||||||
|
|
||||||
|
for (i = 0; i < tok_size; i += 2)
|
||||||
|
{
|
||||||
|
if (tok[i] <= '9')
|
||||||
|
h = tok[i] - '0';
|
||||||
|
else
|
||||||
|
h = (tok[i] - 'A') + 10;
|
||||||
|
if (tok[i+1] <= '9')
|
||||||
|
l = tok[i+1] - '0';
|
||||||
|
else
|
||||||
|
l = (tok[i+1] - 'A') + 10;
|
||||||
|
tok[i/2] = h * 16 + l;
|
||||||
|
}
|
||||||
|
|
||||||
|
out->binary.buff = malloc(out->binary.len);
|
||||||
|
memcpy(out->binary.buff, tok, out->binary.len);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int dat_value_provider(void *ctx, struct rmsgpack_dom_value *out)
|
||||||
|
{
|
||||||
|
int rv, i;
|
||||||
|
static const int field_count = 22;
|
||||||
|
int fd = *((int*)ctx);
|
||||||
|
char* key;
|
||||||
|
|
||||||
|
out->type = RDT_MAP;
|
||||||
|
out->map.len = field_count;
|
||||||
|
out->map.items = calloc(field_count, sizeof(struct rmsgpack_dom_pair));
|
||||||
|
|
||||||
|
if (find_token(fd, "game") < 0)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
for (i = 0; i < field_count; i++)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].key)) < 0)
|
||||||
|
goto failed;
|
||||||
|
|
||||||
|
key = out->map.items[i].key.string.buff;
|
||||||
|
|
||||||
|
if (strncmp(key, "name", sizeof("name")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "description", sizeof("description")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "users", sizeof("users")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_uint(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "releasemonth", sizeof("releasemonth")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_uint(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "releaseyear", sizeof("releaseyear")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_uint(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "rumble", sizeof("rumble")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_uint(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "analog", sizeof("analog")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_uint(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "serial", sizeof("serial")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "esrb_rating", sizeof("esrb_rating")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "elspa_rating", sizeof("elspa_rating")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "pegi_rating", sizeof("pegi_rating")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "cero_rating", sizeof("cero_rating")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "developers", sizeof("developers")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "publisher", sizeof("publisher")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "origin", sizeof("origin")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "rom", sizeof("rom")) == 0)
|
||||||
|
{
|
||||||
|
if (find_token(fd, "name") < 0)
|
||||||
|
goto failed;
|
||||||
|
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "size", sizeof("size")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_uint(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "sha1", sizeof("sha1")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_bin(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "crc", sizeof("crc")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_bin(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "md5", sizeof("md5")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_bin(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, "serial", sizeof("serial")) == 0)
|
||||||
|
{
|
||||||
|
if ((rv = load_string(fd, &out->map.items[i].value)) < 0)
|
||||||
|
goto failed;
|
||||||
|
}
|
||||||
|
else if (strncmp(key, ")", sizeof(")")) == 0)
|
||||||
|
{
|
||||||
|
rmsgpack_dom_value_free(&out->map.items[i].key);
|
||||||
|
out->map.len = i;
|
||||||
|
printf("Couldn't find all fields for item\n");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
rmsgpack_dom_value_free(&out->map.items[i].key);
|
||||||
|
i--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
printf("Inserting '%s' (%02X%02X%02X%02X)...\n",
|
||||||
|
get_map_value(out, "name")->string.buff,
|
||||||
|
(unsigned char)get_map_value(out, "crc")->binary.buff[0],
|
||||||
|
(unsigned char)get_map_value(out, "crc")->binary.buff[1],
|
||||||
|
(unsigned char)get_map_value(out, "crc")->binary.buff[2],
|
||||||
|
(unsigned char)get_map_value(out, "crc")->binary.buff[3]
|
||||||
|
);
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
failed:
|
||||||
|
rmsgpack_dom_value_free(out);
|
||||||
|
out->type = RDT_NULL;
|
||||||
|
return rv;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(int argc, char **argv)
|
||||||
|
{
|
||||||
|
int rv = 0;
|
||||||
|
int src = -1;
|
||||||
|
int dst = -1;
|
||||||
|
if (argc != 3)
|
||||||
|
printf("Usage: %s <dat file> <output file>\n", argv[0]);
|
||||||
|
|
||||||
|
src = open(argv[1], O_RDONLY);
|
||||||
|
if (src == -1)
|
||||||
|
{
|
||||||
|
printf("Could not open source file '%s': %s\n", argv[1], strerror(errno));
|
||||||
|
rv = errno;
|
||||||
|
goto clean;
|
||||||
|
}
|
||||||
|
|
||||||
|
dst = open(argv[2], O_WRONLY | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR);
|
||||||
|
if (dst == -1)
|
||||||
|
{
|
||||||
|
printf("Could not open destination file '%s': %s\n", argv[1], strerror(errno));
|
||||||
|
rv = errno;
|
||||||
|
goto clean;
|
||||||
|
}
|
||||||
|
|
||||||
|
rv = rarchdb_create(dst, &dat_value_provider, &src);
|
||||||
|
|
||||||
|
clean:
|
||||||
|
if (src != -1)
|
||||||
|
close(src);
|
||||||
|
if (dst != -1)
|
||||||
|
close(dst);
|
||||||
|
return rv;
|
||||||
|
}
|
80
libretrodb/db_parser.c
Normal file
80
libretrodb/db_parser.c
Normal file
@ -0,0 +1,80 @@
|
|||||||
|
#include "db_parser.h"
|
||||||
|
|
||||||
|
#include <errno.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
ssize_t get_token(int fd, char *token, size_t max_len)
|
||||||
|
{
|
||||||
|
char *c = token;
|
||||||
|
int rv;
|
||||||
|
ssize_t len = 0;
|
||||||
|
int in_string = 0;
|
||||||
|
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
rv = read(fd, c, 1);
|
||||||
|
if (rv == 0)
|
||||||
|
return 0;
|
||||||
|
else if (rv < 1)
|
||||||
|
{
|
||||||
|
switch (errno)
|
||||||
|
{
|
||||||
|
case EINTR:
|
||||||
|
case EAGAIN:
|
||||||
|
continue;
|
||||||
|
default:
|
||||||
|
return -errno;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (*c)
|
||||||
|
{
|
||||||
|
case ' ':
|
||||||
|
case '\t':
|
||||||
|
case '\r':
|
||||||
|
case '\n':
|
||||||
|
if (c == token)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (!in_string)
|
||||||
|
{
|
||||||
|
*c = '\0';
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case '\"':
|
||||||
|
if (c == token)
|
||||||
|
{
|
||||||
|
in_string = 1;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
*c = '\0';
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
|
len++;
|
||||||
|
c++;
|
||||||
|
if (len == (ssize_t)max_len)
|
||||||
|
{
|
||||||
|
*c = '\0';
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int find_token(int fd, const char *token)
|
||||||
|
{
|
||||||
|
int tmp_len = strlen(token);
|
||||||
|
char *tmp_token = (char*)calloc(tmp_len, 1);
|
||||||
|
if (!tmp_token)
|
||||||
|
return -1;
|
||||||
|
while (strncmp(tmp_token, token, tmp_len) != 0)
|
||||||
|
{
|
||||||
|
if (get_token(fd, tmp_token, tmp_len) <= 0)
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
@ -1,4 +1,4 @@
|
|||||||
#include "rarchdb.h"
|
#include "libretrodb.h"
|
||||||
|
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
@ -17,43 +17,26 @@
|
|||||||
#include "rmsgpack_dom.h"
|
#include "rmsgpack_dom.h"
|
||||||
#include "rmsgpack.h"
|
#include "rmsgpack.h"
|
||||||
#include "bintree.h"
|
#include "bintree.h"
|
||||||
#include "rarchdb_endian.h"
|
#include "libretrodb_endian.h"
|
||||||
#include "query.h"
|
#include "query.h"
|
||||||
|
|
||||||
#define MAGIC_NUMBER "RARCHDB"
|
|
||||||
|
|
||||||
struct rarchdb_header {
|
|
||||||
char magic_number[sizeof(MAGIC_NUMBER)-1];
|
|
||||||
uint64_t metadata_offset;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct rarchdb_metadata {
|
|
||||||
uint64_t count;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct rarchdb_index {
|
|
||||||
char name[50];
|
|
||||||
uint64_t key_size;
|
|
||||||
uint64_t next;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct node_iter_ctx {
|
struct node_iter_ctx {
|
||||||
struct rarchdb * db;
|
libretrodb_t *db;
|
||||||
struct rarchdb_index * idx;
|
libretrodb_index_t *idx;
|
||||||
};
|
};
|
||||||
|
|
||||||
static struct rmsgpack_dom_value sentinal;
|
static struct rmsgpack_dom_value sentinal;
|
||||||
|
|
||||||
static int rarchdb_read_metadata(
|
static int libretrodb_read_metadata(
|
||||||
int fd,
|
int fd,
|
||||||
struct rarchdb_metadata * md
|
libretrodb_metadata_t *md
|
||||||
){
|
){
|
||||||
return rmsgpack_dom_read_into(fd, "count", &md->count, NULL);
|
return rmsgpack_dom_read_into(fd, "count", &md->count, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int rarchdb_write_metadata(
|
static int libretrodb_write_metadata(
|
||||||
int fd,
|
int fd,
|
||||||
struct rarchdb_metadata * md
|
libretrodb_metadata_t *md
|
||||||
){
|
){
|
||||||
rmsgpack_write_map_header(fd, 1);
|
rmsgpack_write_map_header(fd, 1);
|
||||||
rmsgpack_write_string(fd, "count", strlen("count"));
|
rmsgpack_write_string(fd, "count", strlen("count"));
|
||||||
@ -93,24 +76,26 @@ static int validate_document(const struct rmsgpack_dom_value * doc) {
|
|||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
int rarchdb_create(
|
int libretrodb_create(
|
||||||
int fd,
|
int fd,
|
||||||
rarchdb_value_provider value_provider,
|
libretrodb_value_provider value_provider,
|
||||||
void * ctx
|
void * ctx
|
||||||
){
|
){
|
||||||
int rv;
|
int rv;
|
||||||
struct rarchdb_metadata md;
|
off_t root;
|
||||||
off_t root;
|
|
||||||
uint64_t item_count = 0;
|
uint64_t item_count = 0;
|
||||||
|
libretrodb_metadata_t md;
|
||||||
struct rmsgpack_dom_value item = {};
|
struct rmsgpack_dom_value item = {};
|
||||||
struct rarchdb_header header = {};
|
libretrodb_header_t header = {};
|
||||||
|
|
||||||
memcpy(header.magic_number, MAGIC_NUMBER, sizeof(MAGIC_NUMBER)-1);
|
memcpy(header.magic_number, MAGIC_NUMBER, sizeof(MAGIC_NUMBER)-1);
|
||||||
root = lseek(fd, 0, SEEK_CUR);
|
root = lseek(fd, 0, SEEK_CUR);
|
||||||
|
|
||||||
// We write the header in the end because we need to know the size of
|
/* We write the header in the end because we need to know the size of
|
||||||
// the db first
|
* the db first */
|
||||||
lseek(fd, sizeof(struct rarchdb_header), SEEK_CUR);
|
|
||||||
|
lseek(fd, sizeof(libretrodb_header_t), SEEK_CUR);
|
||||||
|
|
||||||
while ((rv = value_provider(ctx, &item)) == 0) {
|
while ((rv = value_provider(ctx, &item)) == 0) {
|
||||||
|
|
||||||
if ((rv = validate_document(&item)) < 0)
|
if ((rv = validate_document(&item)) < 0)
|
||||||
@ -130,7 +115,7 @@ int rarchdb_create(
|
|||||||
|
|
||||||
header.metadata_offset = httobe64(lseek(fd, 0, SEEK_CUR));
|
header.metadata_offset = httobe64(lseek(fd, 0, SEEK_CUR));
|
||||||
md.count = item_count;
|
md.count = item_count;
|
||||||
rarchdb_write_metadata(fd, &md);
|
libretrodb_write_metadata(fd, &md);
|
||||||
lseek(fd, root, SEEK_SET);
|
lseek(fd, root, SEEK_SET);
|
||||||
write(fd, &header, sizeof(header));
|
write(fd, &header, sizeof(header));
|
||||||
clean:
|
clean:
|
||||||
@ -138,10 +123,9 @@ clean:
|
|||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int rarchdb_read_index_header(
|
static int libretrodb_read_index_header(
|
||||||
int fd,
|
int fd, libretrodb_index_t *idx)
|
||||||
struct rarchdb_index * idx
|
{
|
||||||
){
|
|
||||||
uint64_t name_len = 50;
|
uint64_t name_len = 50;
|
||||||
return rmsgpack_dom_read_into(
|
return rmsgpack_dom_read_into(
|
||||||
fd,
|
fd,
|
||||||
@ -152,10 +136,9 @@ static int rarchdb_read_index_header(
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void rarchdb_write_index_header(
|
static void libretrodb_write_index_header(
|
||||||
int fd,
|
int fd, libretrodb_index_t * idx)
|
||||||
struct rarchdb_index * idx
|
{
|
||||||
){
|
|
||||||
rmsgpack_write_map_header(fd, 3);
|
rmsgpack_write_map_header(fd, 3);
|
||||||
rmsgpack_write_string(fd, "name", strlen("name"));
|
rmsgpack_write_string(fd, "name", strlen("name"));
|
||||||
rmsgpack_write_string(fd, idx->name, strlen(idx->name));
|
rmsgpack_write_string(fd, idx->name, strlen(idx->name));
|
||||||
@ -165,20 +148,22 @@ static void rarchdb_write_index_header(
|
|||||||
rmsgpack_write_uint(fd, idx->next);
|
rmsgpack_write_uint(fd, idx->next);
|
||||||
}
|
}
|
||||||
|
|
||||||
void rarchdb_close(struct rarchdb * db)
|
void libretrodb_close(libretrodb_t * db)
|
||||||
{
|
{
|
||||||
close(db->fd);
|
close(db->fd);
|
||||||
db->fd = -1;
|
db->fd = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int rarchdb_open(
|
int libretrodb_open(
|
||||||
const char * path,
|
const char * path,
|
||||||
struct rarchdb * db
|
libretrodb_t * db
|
||||||
){
|
)
|
||||||
struct rarchdb_header header;
|
{
|
||||||
struct rarchdb_metadata md;
|
libretrodb_header_t header;
|
||||||
|
libretrodb_metadata_t md;
|
||||||
int rv;
|
int rv;
|
||||||
int fd = open(path, O_RDWR);
|
int fd = open(path, O_RDWR);
|
||||||
|
|
||||||
if (fd == -1)
|
if (fd == -1)
|
||||||
return -errno;
|
return -errno;
|
||||||
|
|
||||||
@ -195,7 +180,7 @@ int rarchdb_open(
|
|||||||
|
|
||||||
header.metadata_offset = betoht64(header.metadata_offset);
|
header.metadata_offset = betoht64(header.metadata_offset);
|
||||||
lseek(fd, header.metadata_offset, SEEK_SET);
|
lseek(fd, header.metadata_offset, SEEK_SET);
|
||||||
if (rarchdb_read_metadata(fd, &md) < 0) {
|
if (libretrodb_read_metadata(fd, &md) < 0) {
|
||||||
rv = -EINVAL;
|
rv = -EINVAL;
|
||||||
goto error;
|
goto error;
|
||||||
}
|
}
|
||||||
@ -208,19 +193,22 @@ error:
|
|||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int rarchdb_find_index(
|
static int libretrodb_find_index(
|
||||||
struct rarchdb * db,
|
libretrodb_t *db,
|
||||||
const char * index_name,
|
const char *index_name,
|
||||||
struct rarchdb_index * idx
|
libretrodb_index_t *idx
|
||||||
){
|
){
|
||||||
off_t eof = lseek(db->fd, 0, SEEK_END);
|
off_t eof = lseek(db->fd, 0, SEEK_END);
|
||||||
off_t offset = lseek(db->fd, db->first_index_offset, SEEK_SET);
|
off_t offset = lseek(db->fd, db->first_index_offset, SEEK_SET);
|
||||||
while (offset < eof) {
|
|
||||||
rarchdb_read_index_header(db->fd, idx);
|
while (offset < eof)
|
||||||
if (strncmp(index_name, idx->name, strlen(idx->name)) == 0)
|
{
|
||||||
return 0;
|
libretrodb_read_index_header(db->fd, idx);
|
||||||
offset = lseek(db->fd, idx->next, SEEK_CUR);
|
if (strncmp(index_name, idx->name, strlen(idx->name)) == 0)
|
||||||
}
|
return 0;
|
||||||
|
offset = lseek(db->fd, idx->next, SEEK_CUR);
|
||||||
|
}
|
||||||
|
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -255,21 +243,20 @@ static int binsearch(
|
|||||||
return binsearch(current + item_size, item, count - mid, field_size, offset);
|
return binsearch(current + item_size, item, count - mid, field_size, offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
int rarchdb_find_entry(
|
int libretrodb_find_entry(
|
||||||
struct rarchdb * db,
|
libretrodb_t *db,
|
||||||
const char * index_name,
|
const char *index_name,
|
||||||
const void * key,
|
const void *key,
|
||||||
struct rmsgpack_dom_value * out
|
struct rmsgpack_dom_value * out
|
||||||
) {
|
) {
|
||||||
struct rarchdb_index idx;
|
libretrodb_index_t idx;
|
||||||
int rv;
|
int rv;
|
||||||
void * buff;
|
void * buff;
|
||||||
uint64_t offset;
|
uint64_t offset;
|
||||||
ssize_t bufflen, nread = 0;
|
ssize_t bufflen, nread = 0;
|
||||||
|
|
||||||
if (rarchdb_find_index(db, index_name, &idx) < 0) {
|
if (libretrodb_find_index(db, index_name, &idx) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
}
|
|
||||||
|
|
||||||
bufflen = idx.next;
|
bufflen = idx.next;
|
||||||
buff = malloc(bufflen);
|
buff = malloc(bufflen);
|
||||||
@ -302,25 +289,25 @@ int rarchdb_find_entry(
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* rarchdb_cursor_reset:
|
* libretrodb_cursor_reset:
|
||||||
* @cursor : Handle to database cursor.
|
* @cursor : Handle to database cursor.
|
||||||
*
|
*
|
||||||
* Resets cursor.
|
* Resets cursor.
|
||||||
*
|
*
|
||||||
* Returns: ???.
|
* Returns: ???.
|
||||||
**/
|
**/
|
||||||
int rarchdb_cursor_reset(struct rarchdb_cursor * cursor)
|
int libretrodb_cursor_reset(libretrodb_cursor_t *cursor)
|
||||||
{
|
{
|
||||||
cursor->eof = 0;
|
cursor->eof = 0;
|
||||||
return lseek(
|
return lseek(
|
||||||
cursor->fd,
|
cursor->fd,
|
||||||
cursor->db->root + sizeof(struct rarchdb_header),
|
cursor->db->root + sizeof(libretrodb_header_t),
|
||||||
SEEK_SET
|
SEEK_SET
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
int rarchdb_cursor_read_item(
|
int libretrodb_cursor_read_item(
|
||||||
struct rarchdb_cursor * cursor,
|
libretrodb_cursor_t *cursor,
|
||||||
struct rmsgpack_dom_value * out
|
struct rmsgpack_dom_value * out
|
||||||
) {
|
) {
|
||||||
int rv;
|
int rv;
|
||||||
@ -338,7 +325,7 @@ retry:
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (cursor->query) {
|
if (cursor->query) {
|
||||||
if (!rarchdb_query_filter(cursor->query, out)) {
|
if (!libretrodb_query_filter(cursor->query, out)) {
|
||||||
goto retry;
|
goto retry;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -347,12 +334,12 @@ retry:
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* rarchdb_cursor_close:
|
* libretrodb_cursor_close:
|
||||||
* @cursor : Handle to database cursor.
|
* @cursor : Handle to database cursor.
|
||||||
*
|
*
|
||||||
* Closes cursor and frees up allocated memory.
|
* Closes cursor and frees up allocated memory.
|
||||||
**/
|
**/
|
||||||
void rarchdb_cursor_close(struct rarchdb_cursor * cursor)
|
void libretrodb_cursor_close(libretrodb_cursor_t *cursor)
|
||||||
{
|
{
|
||||||
close(cursor->fd);
|
close(cursor->fd);
|
||||||
cursor->is_valid = 0;
|
cursor->is_valid = 0;
|
||||||
@ -360,12 +347,12 @@ void rarchdb_cursor_close(struct rarchdb_cursor * cursor)
|
|||||||
cursor->eof = 1;
|
cursor->eof = 1;
|
||||||
cursor->db = NULL;
|
cursor->db = NULL;
|
||||||
if (cursor->query)
|
if (cursor->query)
|
||||||
rarchdb_query_free(cursor->query);
|
libretrodb_query_free(cursor->query);
|
||||||
cursor->query = NULL;
|
cursor->query = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* rarchdb_cursor_open:
|
* libretrodb_cursor_open:
|
||||||
* @db : Handle to database.
|
* @db : Handle to database.
|
||||||
* @cursor : Handle to database cursor.
|
* @cursor : Handle to database cursor.
|
||||||
* @q : Query to execute.
|
* @q : Query to execute.
|
||||||
@ -374,10 +361,10 @@ void rarchdb_cursor_close(struct rarchdb_cursor * cursor)
|
|||||||
*
|
*
|
||||||
* Returns: 0 if successful, otherwise negative.
|
* Returns: 0 if successful, otherwise negative.
|
||||||
**/
|
**/
|
||||||
int rarchdb_cursor_open(
|
int libretrodb_cursor_open(
|
||||||
struct rarchdb * db,
|
libretrodb_t *db,
|
||||||
struct rarchdb_cursor * cursor,
|
libretrodb_cursor_t *cursor,
|
||||||
rarchdb_query * q
|
libretrodb_query_t *q
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
cursor->fd = dup(db->fd);
|
cursor->fd = dup(db->fd);
|
||||||
@ -387,11 +374,11 @@ int rarchdb_cursor_open(
|
|||||||
|
|
||||||
cursor->db = db;
|
cursor->db = db;
|
||||||
cursor->is_valid = 1;
|
cursor->is_valid = 1;
|
||||||
rarchdb_cursor_reset(cursor);
|
libretrodb_cursor_reset(cursor);
|
||||||
cursor->query = q;
|
cursor->query = q;
|
||||||
|
|
||||||
if (q)
|
if (q)
|
||||||
rarchdb_query_inc_ref(q);
|
libretrodb_query_inc_ref(q);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -406,41 +393,41 @@ static int node_iter(void * value, void * ctx)
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint64_t rarchdb_tell(struct rarchdb * db)
|
static uint64_t libretrodb_tell(libretrodb_t *db)
|
||||||
{
|
{
|
||||||
return lseek(db->fd, 0, SEEK_CUR);
|
return lseek(db->fd, 0, SEEK_CUR);
|
||||||
}
|
}
|
||||||
|
|
||||||
int rarchdb_create_index(
|
int libretrodb_create_index(
|
||||||
struct rarchdb * db,
|
libretrodb_t *db,
|
||||||
const char * name,
|
const char *name,
|
||||||
const char * field_name
|
const char *field_name
|
||||||
){
|
){
|
||||||
int rv;
|
int rv;
|
||||||
struct node_iter_ctx nictx;
|
struct node_iter_ctx nictx;
|
||||||
struct rmsgpack_dom_value key;
|
struct rmsgpack_dom_value key;
|
||||||
struct rarchdb_index idx;
|
libretrodb_index_t idx;
|
||||||
struct rmsgpack_dom_value item;
|
struct rmsgpack_dom_value item;
|
||||||
struct rmsgpack_dom_value * field;
|
struct rmsgpack_dom_value * field;
|
||||||
|
struct bintree tree;
|
||||||
|
libretrodb_cursor_t cur;
|
||||||
void * buff = NULL;
|
void * buff = NULL;
|
||||||
uint64_t * buff_u64 = NULL;
|
uint64_t * buff_u64 = NULL;
|
||||||
uint8_t field_size = 0;
|
uint8_t field_size = 0;
|
||||||
struct bintree tree;
|
|
||||||
uint64_t item_loc = rarchdb_tell(db);
|
|
||||||
uint64_t idx_header_offset;
|
uint64_t idx_header_offset;
|
||||||
struct rarchdb_cursor cur;
|
uint64_t item_loc = libretrodb_tell(db);
|
||||||
|
|
||||||
bintree_new(&tree, node_compare, &field_size);
|
bintree_new(&tree, node_compare, &field_size);
|
||||||
if (rarchdb_cursor_open(db, &cur, NULL) != 0) {
|
if (libretrodb_cursor_open(db, &cur, NULL) != 0) {
|
||||||
rv = -1;
|
rv = -1;
|
||||||
goto clean;
|
goto clean;
|
||||||
}
|
}
|
||||||
|
|
||||||
key.type = RDT_STRING;
|
key.type = RDT_STRING;
|
||||||
key.string.len = strlen(field_name);
|
key.string.len = strlen(field_name);
|
||||||
// We know we aren't going to change it
|
/* We know we aren't going to change it */
|
||||||
key.string.buff = (char *) field_name;
|
key.string.buff = (char *) field_name;
|
||||||
while (rarchdb_cursor_read_item(&cur, &item) == 0) {
|
while (libretrodb_cursor_read_item(&cur, &item) == 0) {
|
||||||
if (item.type != RDT_MAP) {
|
if (item.type != RDT_MAP) {
|
||||||
rv = -EINVAL;
|
rv = -EINVAL;
|
||||||
printf("Only map keys are supported\n");
|
printf("Only map keys are supported\n");
|
||||||
@ -491,7 +478,7 @@ int rarchdb_create_index(
|
|||||||
}
|
}
|
||||||
buff = NULL;
|
buff = NULL;
|
||||||
rmsgpack_dom_value_free(&item);
|
rmsgpack_dom_value_free(&item);
|
||||||
item_loc = rarchdb_tell(db);
|
item_loc = libretrodb_tell(db);
|
||||||
}
|
}
|
||||||
|
|
||||||
(void)rv;
|
(void)rv;
|
||||||
@ -503,7 +490,7 @@ int rarchdb_create_index(
|
|||||||
idx.name[49] = '\0';
|
idx.name[49] = '\0';
|
||||||
idx.key_size = field_size;
|
idx.key_size = field_size;
|
||||||
idx.next = db->count * (field_size + sizeof(uint64_t));
|
idx.next = db->count * (field_size + sizeof(uint64_t));
|
||||||
rarchdb_write_index_header(db->fd, &idx);
|
libretrodb_write_index_header(db->fd, &idx);
|
||||||
|
|
||||||
nictx.db = db;
|
nictx.db = db;
|
||||||
nictx.idx = &idx;
|
nictx.idx = &idx;
|
||||||
@ -514,7 +501,7 @@ clean:
|
|||||||
if (buff)
|
if (buff)
|
||||||
free(buff);
|
free(buff);
|
||||||
if (cur.is_valid) {
|
if (cur.is_valid) {
|
||||||
rarchdb_cursor_close(&cur);
|
libretrodb_cursor_close(&cur);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
129
libretrodb/libretrodb.h
Normal file
129
libretrodb/libretrodb.h
Normal file
@ -0,0 +1,129 @@
|
|||||||
|
#ifndef __LIBRETRODB_H__
|
||||||
|
#define __LIBRETRODB_H__
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#ifdef _WIN32
|
||||||
|
#include <direct.h>
|
||||||
|
#else
|
||||||
|
#include <unistd.h>
|
||||||
|
#endif
|
||||||
|
#include "rmsgpack_dom.h"
|
||||||
|
|
||||||
|
#define MAGIC_NUMBER "RARCHDB"
|
||||||
|
|
||||||
|
typedef struct libretrodb_query libretrodb_query_t;
|
||||||
|
|
||||||
|
typedef struct libretrodb
|
||||||
|
{
|
||||||
|
int fd;
|
||||||
|
uint64_t root;
|
||||||
|
uint64_t count;
|
||||||
|
uint64_t first_index_offset;
|
||||||
|
} libretrodb_t;
|
||||||
|
|
||||||
|
typedef struct libretrodb_index
|
||||||
|
{
|
||||||
|
char name[50];
|
||||||
|
uint64_t key_size;
|
||||||
|
uint64_t next;
|
||||||
|
} libretrodb_index_t;
|
||||||
|
|
||||||
|
typedef struct libretrodb_metadata
|
||||||
|
{
|
||||||
|
uint64_t count;
|
||||||
|
} libretrodb_metadata_t;
|
||||||
|
|
||||||
|
typedef struct libretrodb_header
|
||||||
|
{
|
||||||
|
char magic_number[sizeof(MAGIC_NUMBER)-1];
|
||||||
|
uint64_t metadata_offset;
|
||||||
|
} libretrodb_header_t;
|
||||||
|
|
||||||
|
typedef struct libretrodb_cursor
|
||||||
|
{
|
||||||
|
int is_valid;
|
||||||
|
int fd;
|
||||||
|
int eof;
|
||||||
|
libretrodb_query_t * query;
|
||||||
|
libretrodb_t * db;
|
||||||
|
} libretrodb_cursor_t;
|
||||||
|
|
||||||
|
typedef int (* libretrodb_value_provider)(
|
||||||
|
void * ctx,
|
||||||
|
struct rmsgpack_dom_value * out
|
||||||
|
);
|
||||||
|
|
||||||
|
int libretrodb_create(
|
||||||
|
int fd,
|
||||||
|
libretrodb_value_provider value_provider,
|
||||||
|
void * ctx
|
||||||
|
);
|
||||||
|
|
||||||
|
void libretrodb_close(libretrodb_t * db);
|
||||||
|
|
||||||
|
int libretrodb_open(
|
||||||
|
const char * path,
|
||||||
|
libretrodb_t * db
|
||||||
|
);
|
||||||
|
|
||||||
|
int libretrodb_create_index(
|
||||||
|
libretrodb_t * db,
|
||||||
|
const char * name,
|
||||||
|
const char * field_name
|
||||||
|
);
|
||||||
|
int libretrodb_find_entry(
|
||||||
|
libretrodb_t * db,
|
||||||
|
const char * index_name,
|
||||||
|
const void * key,
|
||||||
|
struct rmsgpack_dom_value * out
|
||||||
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* libretrodb_cursor_open:
|
||||||
|
* @db : Handle to database.
|
||||||
|
* @cursor : Handle to database cursor.
|
||||||
|
* @q : Query to execute.
|
||||||
|
*
|
||||||
|
* Opens cursor to database based on query @q.
|
||||||
|
*
|
||||||
|
* Returns: 0 if successful, otherwise negative.
|
||||||
|
**/
|
||||||
|
int libretrodb_cursor_open(
|
||||||
|
libretrodb_t *db,
|
||||||
|
libretrodb_cursor_t *cursor,
|
||||||
|
libretrodb_query_t *query
|
||||||
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* libretrodb_cursor_reset:
|
||||||
|
* @cursor : Handle to database cursor.
|
||||||
|
*
|
||||||
|
* Resets cursor.
|
||||||
|
*
|
||||||
|
* Returns: ???.
|
||||||
|
**/
|
||||||
|
int libretrodb_cursor_reset(libretrodb_cursor_t * cursor);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* libretrodb_cursor_close:
|
||||||
|
* @cursor : Handle to database cursor.
|
||||||
|
*
|
||||||
|
* Closes cursor and frees up allocated memory.
|
||||||
|
**/
|
||||||
|
void libretrodb_cursor_close(libretrodb_cursor_t * cursor);
|
||||||
|
|
||||||
|
void *libretrodb_query_compile(
|
||||||
|
libretrodb_t * db,
|
||||||
|
const char * query,
|
||||||
|
size_t buff_len,
|
||||||
|
const char ** error
|
||||||
|
);
|
||||||
|
|
||||||
|
void libretrodb_query_free(void *q);
|
||||||
|
|
||||||
|
int libretrodb_cursor_read_item(
|
||||||
|
libretrodb_cursor_t * cursor,
|
||||||
|
struct rmsgpack_dom_value * out
|
||||||
|
);
|
||||||
|
|
||||||
|
#endif
|
@ -1,5 +1,5 @@
|
|||||||
#ifndef __RARCHDB_MSGPACK_ENDIAN_H
|
#ifndef __LIBRETRODB_MSGPACK_ENDIAN_H
|
||||||
#define __RARCHDB_MSGPACK_ENDIAN_H
|
#define __LIBRETRODB_MSGPACK_ENDIAN_H
|
||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <retro_endianness.h>
|
#include <retro_endianness.h>
|
@ -1,7 +1,7 @@
|
|||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
#include "rarchdb.h"
|
#include "libretrodb.h"
|
||||||
#include "rmsgpack_dom.h"
|
#include "rmsgpack_dom.h"
|
||||||
|
|
||||||
int main(
|
int main(
|
||||||
@ -9,9 +9,12 @@ int main(
|
|||||||
char ** argv
|
char ** argv
|
||||||
){
|
){
|
||||||
int rv;
|
int rv;
|
||||||
struct rarchdb db;
|
libretrodb_t db;
|
||||||
struct rarchdb_cursor cur;
|
libretrodb_cursor_t cur;
|
||||||
|
libretrodb_query_t *q;
|
||||||
struct rmsgpack_dom_value item;
|
struct rmsgpack_dom_value item;
|
||||||
|
const char *command, *path, *query_exp, *error;
|
||||||
|
|
||||||
if (argc < 3) {
|
if (argc < 3) {
|
||||||
printf("Usage: %s <db file> <command> [extra args...]\n", argv[0]);
|
printf("Usage: %s <db file> <command> [extra args...]\n", argv[0]);
|
||||||
printf("Available Commands:\n");
|
printf("Available Commands:\n");
|
||||||
@ -21,14 +24,14 @@ int main(
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
const char * command = argv[2];
|
command = argv[2];
|
||||||
const char * path = argv[1];
|
path = argv[1];
|
||||||
|
|
||||||
if ((rv = rarchdb_open(path, &db)) != 0) {
|
if ((rv = libretrodb_open(path, &db)) != 0) {
|
||||||
printf("Could not open db file '%s': %s\n", path, strerror(-rv));
|
printf("Could not open db file '%s': %s\n", path, strerror(-rv));
|
||||||
return 1;
|
return 1;
|
||||||
} else if (strcmp(command, "list") == 0) {
|
} else if (strcmp(command, "list") == 0) {
|
||||||
if ((rv = rarchdb_cursor_open(&db, &cur, NULL)) != 0) {
|
if ((rv = libretrodb_cursor_open(&db, &cur, NULL)) != 0) {
|
||||||
printf("Could not open cursor: %s\n", strerror(-rv));
|
printf("Could not open cursor: %s\n", strerror(-rv));
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
@ -37,7 +40,7 @@ int main(
|
|||||||
printf("Usage: %s <db file> list\n", argv[0]);
|
printf("Usage: %s <db file> list\n", argv[0]);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
while (rarchdb_cursor_read_item(&cur, &item) == 0) {
|
while (libretrodb_cursor_read_item(&cur, &item) == 0) {
|
||||||
rmsgpack_dom_value_print(&item);
|
rmsgpack_dom_value_print(&item);
|
||||||
printf("\n");
|
printf("\n");
|
||||||
rmsgpack_dom_value_free(&item);
|
rmsgpack_dom_value_free(&item);
|
||||||
@ -47,20 +50,23 @@ int main(
|
|||||||
printf("Usage: %s <db file> find <query expression>\n", argv[0]);
|
printf("Usage: %s <db file> find <query expression>\n", argv[0]);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
const char * query_exp = argv[3];
|
|
||||||
const char * error = NULL;
|
query_exp = argv[3];
|
||||||
rarchdb_query * q = rarchdb_query_compile(&db, query_exp, strlen(query_exp), &error);
|
error = NULL;
|
||||||
|
q = libretrodb_query_compile(&db, query_exp, strlen(query_exp), &error);
|
||||||
if (error) {
|
if (error) {
|
||||||
printf("%s\n", error);
|
printf("%s\n", error);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((rv = rarchdb_cursor_open(&db, &cur, q)) != 0) {
|
if ((rv = libretrodb_cursor_open(&db, &cur, q)) != 0)
|
||||||
|
{
|
||||||
printf("Could not open cursor: %s\n", strerror(-rv));
|
printf("Could not open cursor: %s\n", strerror(-rv));
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
while (rarchdb_cursor_read_item(&cur, &item) == 0) {
|
while (libretrodb_cursor_read_item(&cur, &item) == 0)
|
||||||
|
{
|
||||||
rmsgpack_dom_value_print(&item);
|
rmsgpack_dom_value_print(&item);
|
||||||
printf("\n");
|
printf("\n");
|
||||||
rmsgpack_dom_value_free(&item);
|
rmsgpack_dom_value_free(&item);
|
||||||
@ -76,10 +82,10 @@ int main(
|
|||||||
index_name = argv[3];
|
index_name = argv[3];
|
||||||
field_name = argv[4];
|
field_name = argv[4];
|
||||||
|
|
||||||
rarchdb_create_index(&db, index_name, field_name);
|
libretrodb_create_index(&db, index_name, field_name);
|
||||||
} else {
|
} else {
|
||||||
printf("Unkonwn command %s\n", argv[2]);
|
printf("Unkonwn command %s\n", argv[2]);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
rarchdb_close(&db);
|
libretrodb_close(&db);
|
||||||
}
|
}
|
@ -3,7 +3,7 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
int rarchdb_lua_to_rmsgpack_value(
|
int libretrodb_lua_to_rmsgpack_value(
|
||||||
lua_State * L,
|
lua_State * L,
|
||||||
int index,
|
int index,
|
||||||
struct rmsgpack_dom_value * out
|
struct rmsgpack_dom_value * out
|
||||||
|
@ -7,7 +7,7 @@
|
|||||||
|
|
||||||
#include "rmsgpack_dom.h"
|
#include "rmsgpack_dom.h"
|
||||||
|
|
||||||
int rarchdb_lua_to_rmsgpack_value(
|
int libretrodb_lua_to_rmsgpack_value(
|
||||||
lua_State * L,
|
lua_State * L,
|
||||||
int index,
|
int index,
|
||||||
struct rmsgpack_dom_value * out
|
struct rmsgpack_dom_value * out
|
||||||
|
@ -10,7 +10,7 @@
|
|||||||
#include <lualib.h>
|
#include <lualib.h>
|
||||||
#include <lauxlib.h>
|
#include <lauxlib.h>
|
||||||
|
|
||||||
#include "rarchdb.h"
|
#include "libretrodb.h"
|
||||||
#include "lua_common.h"
|
#include "lua_common.h"
|
||||||
|
|
||||||
int master_key = 1;
|
int master_key = 1;
|
||||||
@ -62,7 +62,7 @@ static int value_provider(
|
|||||||
if (lua_isnil(L, -1)) {
|
if (lua_isnil(L, -1)) {
|
||||||
rv = 1;
|
rv = 1;
|
||||||
} else if (lua_istable(L, -1)) {
|
} else if (lua_istable(L, -1)) {
|
||||||
rv = rarchdb_lua_to_rmsgpack_value(L, -1, out);
|
rv = libretrodb_lua_to_rmsgpack_value(L, -1, out);
|
||||||
} else {
|
} else {
|
||||||
printf("function `get_value' must return a table or nil\n");
|
printf("function `get_value' must return a table or nil\n");
|
||||||
}
|
}
|
||||||
@ -108,7 +108,7 @@ int main(
|
|||||||
goto clean;
|
goto clean;
|
||||||
}
|
}
|
||||||
|
|
||||||
rv = rarchdb_create(dst, &value_provider, L);
|
rv = libretrodb_create(dst, &value_provider, L);
|
||||||
clean:
|
clean:
|
||||||
lua_close(L);
|
lua_close(L);
|
||||||
if (dst != -1) {
|
if (dst != -1) {
|
||||||
|
@ -8,7 +8,7 @@
|
|||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
#include "rarchdb.h"
|
#include "libretrodb.h"
|
||||||
|
|
||||||
#include "rmsgpack_dom.h"
|
#include "rmsgpack_dom.h"
|
||||||
#include <compat/fnmatch.h>
|
#include <compat/fnmatch.h>
|
||||||
@ -870,31 +870,30 @@ success:
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void rarchdb_query_free(rarchdb_query * q) {
|
void libretrodb_query_free(void *q)
|
||||||
|
{
|
||||||
unsigned i;
|
unsigned i;
|
||||||
struct query * real_q = (struct query*)q;
|
struct query * real_q = (struct query*)q;
|
||||||
|
|
||||||
real_q->ref_count--;
|
real_q->ref_count--;
|
||||||
if (real_q->ref_count > 0) {
|
if (real_q->ref_count > 0)
|
||||||
return;
|
return;
|
||||||
}
|
|
||||||
|
|
||||||
for (i = 0; i < real_q->root.argc; i++) {
|
for (i = 0; i < real_q->root.argc; i++)
|
||||||
argument_free(&real_q->root.argv[i]);
|
argument_free(&real_q->root.argv[i]);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
rarchdb_query * rarchdb_query_compile(
|
void *libretrodb_query_compile(
|
||||||
struct rarchdb * db,
|
libretrodb_t * db,
|
||||||
const char * query,
|
const char * query,
|
||||||
size_t buff_len,
|
size_t buff_len,
|
||||||
const char ** error
|
const char ** error
|
||||||
) {
|
)
|
||||||
|
{
|
||||||
struct buffer buff;
|
struct buffer buff;
|
||||||
struct query *q = (struct query*)malloc(sizeof(struct query));
|
struct query *q = (struct query*)malloc(sizeof(struct query));
|
||||||
if (!q) {
|
if (!q)
|
||||||
goto clean;
|
goto clean;
|
||||||
}
|
|
||||||
memset(q, 0, sizeof(struct query));
|
memset(q, 0, sizeof(struct query));
|
||||||
q->ref_count = 1;
|
q->ref_count = 1;
|
||||||
buff.data = query;
|
buff.data = query;
|
||||||
@ -914,9 +913,8 @@ rarchdb_query * rarchdb_query_compile(
|
|||||||
}
|
}
|
||||||
|
|
||||||
buff = expect_eof(buff, error);
|
buff = expect_eof(buff, error);
|
||||||
if (*error) {
|
if (*error)
|
||||||
goto clean;
|
goto clean;
|
||||||
}
|
|
||||||
|
|
||||||
if (q->root.func == NULL) {
|
if (q->root.func == NULL) {
|
||||||
raise_unexpected_eof(buff.offset, error);
|
raise_unexpected_eof(buff.offset, error);
|
||||||
@ -924,20 +922,20 @@ rarchdb_query * rarchdb_query_compile(
|
|||||||
}
|
}
|
||||||
goto success;
|
goto success;
|
||||||
clean:
|
clean:
|
||||||
if (q) {
|
if (q)
|
||||||
rarchdb_query_free(q);
|
libretrodb_query_free(q);
|
||||||
}
|
|
||||||
success:
|
success:
|
||||||
return q;
|
return q;
|
||||||
}
|
}
|
||||||
|
|
||||||
void rarchdb_query_inc_ref(rarchdb_query * q) {
|
void libretrodb_query_inc_ref(libretrodb_query_t *q)
|
||||||
|
{
|
||||||
struct query * rq = (struct query*)q;
|
struct query * rq = (struct query*)q;
|
||||||
rq->ref_count += 1;
|
rq->ref_count += 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int rarchdb_query_filter(
|
int libretrodb_query_filter(
|
||||||
rarchdb_query * q,
|
libretrodb_query_t * q,
|
||||||
struct rmsgpack_dom_value * v
|
struct rmsgpack_dom_value * v
|
||||||
) {
|
) {
|
||||||
struct invocation inv = ((struct query *)q)->root;
|
struct invocation inv = ((struct query *)q)->root;
|
||||||
|
@ -1,12 +1,14 @@
|
|||||||
#ifndef __RARCHDB_QUERY_H__
|
#ifndef __LIBRETRODB_QUERY_H__
|
||||||
#define __RARCHDB_QUERY_H__
|
#define __LIBRETRODB_QUERY_H__
|
||||||
|
|
||||||
#include "rarchdb.h"
|
#include "libretrodb.h"
|
||||||
|
|
||||||
void rarchdb_query_inc_ref(rarchdb_query * q);
|
void libretrodb_query_inc_ref(libretrodb_query_t *q);
|
||||||
void rarchdb_query_dec_ref(rarchdb_query * q);
|
|
||||||
int rarchdb_query_filter(
|
void libretrodb_query_dec_ref(libretrodb_query_t *q);
|
||||||
rarchdb_query * q,
|
|
||||||
|
int libretrodb_query_filter(
|
||||||
|
libretrodb_query_t *q,
|
||||||
struct rmsgpack_dom_value * v
|
struct rmsgpack_dom_value * v
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -1,108 +0,0 @@
|
|||||||
#ifndef __RARCHDB_H__
|
|
||||||
#define __RARCHDB_H__
|
|
||||||
|
|
||||||
#include <stdint.h>
|
|
||||||
#ifdef _WIN32
|
|
||||||
#include <direct.h>
|
|
||||||
#else
|
|
||||||
#include <unistd.h>
|
|
||||||
#endif
|
|
||||||
#include "rmsgpack_dom.h"
|
|
||||||
|
|
||||||
typedef void rarchdb_query;
|
|
||||||
|
|
||||||
struct rarchdb
|
|
||||||
{
|
|
||||||
int fd;
|
|
||||||
uint64_t root;
|
|
||||||
uint64_t count;
|
|
||||||
uint64_t first_index_offset;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct rarchdb_cursor
|
|
||||||
{
|
|
||||||
int is_valid;
|
|
||||||
int fd;
|
|
||||||
int eof;
|
|
||||||
rarchdb_query * query;
|
|
||||||
struct rarchdb * db;
|
|
||||||
};
|
|
||||||
|
|
||||||
typedef int (* rarchdb_value_provider)(
|
|
||||||
void * ctx,
|
|
||||||
struct rmsgpack_dom_value * out
|
|
||||||
);
|
|
||||||
|
|
||||||
int rarchdb_create(
|
|
||||||
int fd,
|
|
||||||
rarchdb_value_provider value_provider,
|
|
||||||
void * ctx
|
|
||||||
);
|
|
||||||
|
|
||||||
void rarchdb_close(struct rarchdb * db);
|
|
||||||
|
|
||||||
int rarchdb_open(
|
|
||||||
const char * path,
|
|
||||||
struct rarchdb * db
|
|
||||||
);
|
|
||||||
|
|
||||||
int rarchdb_create_index(
|
|
||||||
struct rarchdb * db,
|
|
||||||
const char * name,
|
|
||||||
const char * field_name
|
|
||||||
);
|
|
||||||
int rarchdb_find_entry(
|
|
||||||
struct rarchdb * db,
|
|
||||||
const char * index_name,
|
|
||||||
const void * key,
|
|
||||||
struct rmsgpack_dom_value * out
|
|
||||||
);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* rarchdb_cursor_open:
|
|
||||||
* @db : Handle to database.
|
|
||||||
* @cursor : Handle to database cursor.
|
|
||||||
* @q : Query to execute.
|
|
||||||
*
|
|
||||||
* Opens cursor to database based on query @q.
|
|
||||||
*
|
|
||||||
* Returns: 0 if successful, otherwise negative.
|
|
||||||
**/
|
|
||||||
int rarchdb_cursor_open(
|
|
||||||
struct rarchdb * db,
|
|
||||||
struct rarchdb_cursor * cursor,
|
|
||||||
rarchdb_query * query
|
|
||||||
);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* rarchdb_cursor_reset:
|
|
||||||
* @cursor : Handle to database cursor.
|
|
||||||
*
|
|
||||||
* Resets cursor.
|
|
||||||
*
|
|
||||||
* Returns: ???.
|
|
||||||
**/
|
|
||||||
int rarchdb_cursor_reset(struct rarchdb_cursor * cursor);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* rarchdb_cursor_close:
|
|
||||||
* @cursor : Handle to database cursor.
|
|
||||||
*
|
|
||||||
* Closes cursor and frees up allocated memory.
|
|
||||||
**/
|
|
||||||
void rarchdb_cursor_close(struct rarchdb_cursor * cursor);
|
|
||||||
|
|
||||||
rarchdb_query * rarchdb_query_compile(
|
|
||||||
struct rarchdb * db,
|
|
||||||
const char * query,
|
|
||||||
size_t buff_len,
|
|
||||||
const char ** error
|
|
||||||
);
|
|
||||||
void rarchdb_query_free(rarchdb_query * q);
|
|
||||||
|
|
||||||
int rarchdb_cursor_read_item(
|
|
||||||
struct rarchdb_cursor * cursor,
|
|
||||||
struct rmsgpack_dom_value * out
|
|
||||||
);
|
|
||||||
|
|
||||||
#endif
|
|
@ -21,7 +21,7 @@
|
|||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
#include "rarchdb_endian.h"
|
#include "libretrodb_endian.h"
|
||||||
|
|
||||||
static const uint8_t MPF_FIXMAP = 0x80;
|
static const uint8_t MPF_FIXMAP = 0x80;
|
||||||
static const uint8_t MPF_MAP16 = 0xde;
|
static const uint8_t MPF_MAP16 = 0xde;
|
||||||
|
@ -10,7 +10,7 @@
|
|||||||
#include "lua.h"
|
#include "lua.h"
|
||||||
#include "lauxlib.h"
|
#include "lauxlib.h"
|
||||||
|
|
||||||
#include "rarchdb.h"
|
#include "libretrodb.h"
|
||||||
#include "lua_common.h"
|
#include "lua_common.h"
|
||||||
|
|
||||||
static int create_db (lua_State * L);
|
static int create_db (lua_State * L);
|
||||||
@ -36,7 +36,7 @@ static const struct luaL_Reg cursor_mt [] = {
|
|||||||
{NULL, NULL}
|
{NULL, NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
static const struct luaL_Reg rarchdb_mt [] = {
|
static const struct luaL_Reg libretrodb_mt [] = {
|
||||||
{"__gc", db_close},
|
{"__gc", db_close},
|
||||||
{"list_all", db_cursor_open},
|
{"list_all", db_cursor_open},
|
||||||
{"query", db_query},
|
{"query", db_query},
|
||||||
@ -49,7 +49,7 @@ LUALIB_API int luaopen_testlib (lua_State * L) {
|
|||||||
lua_pushstring(L, "__index");
|
lua_pushstring(L, "__index");
|
||||||
lua_pushvalue(L, -2);
|
lua_pushvalue(L, -2);
|
||||||
lua_settable(L, -3);
|
lua_settable(L, -3);
|
||||||
luaL_openlib(L, NULL, rarchdb_mt, 0);
|
luaL_openlib(L, NULL, libretrodb_mt, 0);
|
||||||
|
|
||||||
luaL_newmetatable(L, "RarchDB.Cursor");
|
luaL_newmetatable(L, "RarchDB.Cursor");
|
||||||
lua_pushstring(L, "__index");
|
lua_pushstring(L, "__index");
|
||||||
@ -61,13 +61,13 @@ LUALIB_API int luaopen_testlib (lua_State * L) {
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct rarchdb_cursor * checkcursor(lua_State * L) {
|
static libretrodb_cursor * checkcursor(lua_State * L) {
|
||||||
void * ud = luaL_checkudata(L, 1, "RarchDB.Cursor");
|
void * ud = luaL_checkudata(L, 1, "RarchDB.Cursor");
|
||||||
luaL_argcheck(L, ud != NULL, 1, "`RarchDB.Cursor' expected");
|
luaL_argcheck(L, ud != NULL, 1, "`RarchDB.Cursor' expected");
|
||||||
return ud;
|
return ud;
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct rarchdb * checkdb(lua_State * L) {
|
static libretrodb * checkdb(lua_State * L) {
|
||||||
void * ud = luaL_checkudata(L, 1, "RarchDB.DB");
|
void * ud = luaL_checkudata(L, 1, "RarchDB.DB");
|
||||||
luaL_argcheck(L, ud != NULL, 1, "`RarchDB.DB' expected");
|
luaL_argcheck(L, ud != NULL, 1, "`RarchDB.DB' expected");
|
||||||
return ud;
|
return ud;
|
||||||
@ -92,7 +92,7 @@ static int value_provider(
|
|||||||
if (lua_isnil(L, -1)) {
|
if (lua_isnil(L, -1)) {
|
||||||
rv = 1;
|
rv = 1;
|
||||||
} else if (lua_istable(L, -1)) {
|
} else if (lua_istable(L, -1)) {
|
||||||
rv = rarchdb_lua_to_rmsgpack_value(L, -1, out);
|
rv = libretrodb_lua_to_rmsgpack_value(L, -1, out);
|
||||||
} else {
|
} else {
|
||||||
printf("function `get_value' must return a table or nil\n");
|
printf("function `get_value' must return a table or nil\n");
|
||||||
}
|
}
|
||||||
@ -117,18 +117,18 @@ static int create_db (lua_State * L) {
|
|||||||
lua_error(L);
|
lua_error(L);
|
||||||
}
|
}
|
||||||
|
|
||||||
rv = rarchdb_create(dst, &value_provider, L);
|
rv = libretrodb_create(dst, &value_provider, L);
|
||||||
close(dst);
|
close(dst);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int db_new (lua_State * L) {
|
static int db_new (lua_State * L) {
|
||||||
struct rarchdb * db = NULL;
|
libretrodb_t * db = NULL;
|
||||||
const char * db_file = NULL;
|
const char * db_file = NULL;
|
||||||
int rv;
|
int rv;
|
||||||
db_file = luaL_checkstring(L, -1);
|
db_file = luaL_checkstring(L, -1);
|
||||||
db = lua_newuserdata(L, sizeof(struct rarchdb));
|
db = lua_newuserdata(L, sizeof(libretrodb_t));
|
||||||
if ((rv = rarchdb_open(db_file, db)) == 0) {
|
if ((rv = libretrodb_open(db_file, db)) == 0) {
|
||||||
luaL_getmetatable(L, "RarchDB.DB");
|
luaL_getmetatable(L, "RarchDB.DB");
|
||||||
lua_setmetatable(L, -2);
|
lua_setmetatable(L, -2);
|
||||||
lua_pushnil(L);
|
lua_pushnil(L);
|
||||||
@ -141,18 +141,18 @@ static int db_new (lua_State * L) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static int db_close (lua_State * L) {
|
static int db_close (lua_State * L) {
|
||||||
struct rarchdb * db = checkdb(L);
|
libretrodb_t *db = checkdb(L);
|
||||||
rarchdb_close(db);
|
libretrodb_close(db);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int db_query (lua_State * L) {
|
static int db_query (lua_State * L) {
|
||||||
int rv;
|
int rv;
|
||||||
struct rarchdb_cursor * cursor = NULL;
|
libretrodb_cursor_t *cursor = NULL;
|
||||||
struct rarchdb * db = checkdb(L);
|
libretrodb_t *db = checkdb(L);
|
||||||
const char * query = luaL_checkstring(L, -1);
|
const char * query = luaL_checkstring(L, -1);
|
||||||
const char * error = NULL;
|
const char * error = NULL;
|
||||||
rarchdb_query * q = rarchdb_query_compile(
|
libretrodb_query_t *q = libretrodb_query_compile(
|
||||||
db,
|
db,
|
||||||
query,
|
query,
|
||||||
strlen(query),
|
strlen(query),
|
||||||
@ -162,8 +162,8 @@ static int db_query (lua_State * L) {
|
|||||||
lua_pushnil(L);
|
lua_pushnil(L);
|
||||||
lua_pushstring(L, error);
|
lua_pushstring(L, error);
|
||||||
} else {
|
} else {
|
||||||
cursor = lua_newuserdata(L, sizeof(struct rarchdb));
|
cursor = lua_newuserdata(L, sizeof(libretrodb_t));
|
||||||
if ((rv = rarchdb_cursor_open(db, cursor, q)) == 0) {
|
if ((rv = libretrodb_cursor_open(db, cursor, q)) == 0) {
|
||||||
luaL_getmetatable(L, "RarchDB.Cursor");
|
luaL_getmetatable(L, "RarchDB.Cursor");
|
||||||
lua_setmetatable(L, -2);
|
lua_setmetatable(L, -2);
|
||||||
lua_pushnil(L);
|
lua_pushnil(L);
|
||||||
@ -172,16 +172,16 @@ static int db_query (lua_State * L) {
|
|||||||
lua_pushnil(L);
|
lua_pushnil(L);
|
||||||
lua_pushstring(L, strerror(-rv));
|
lua_pushstring(L, strerror(-rv));
|
||||||
}
|
}
|
||||||
rarchdb_query_free(q);
|
libretrodb_query_free(q);
|
||||||
}
|
}
|
||||||
return 2;
|
return 2;
|
||||||
}
|
}
|
||||||
static int db_cursor_open (lua_State * L) {
|
static int db_cursor_open (lua_State * L) {
|
||||||
int rv;
|
int rv;
|
||||||
struct rarchdb_cursor * cursor = NULL;
|
libretrodb_cursor_t *cursor = NULL;
|
||||||
struct rarchdb * db = checkdb(L);
|
libretrodb_t *db = checkdb(L);
|
||||||
cursor = lua_newuserdata(L, sizeof(struct rarchdb));
|
cursor = lua_newuserdata(L, sizeof(libretrodb_t));
|
||||||
if ((rv = rarchdb_cursor_open(db, cursor, NULL)) == 0) {
|
if ((rv = libretrodb_cursor_open(db, cursor, NULL)) == 0) {
|
||||||
luaL_getmetatable(L, "RarchDB.Cursor");
|
luaL_getmetatable(L, "RarchDB.Cursor");
|
||||||
lua_setmetatable(L, -2);
|
lua_setmetatable(L, -2);
|
||||||
lua_pushnil(L);
|
lua_pushnil(L);
|
||||||
@ -193,8 +193,8 @@ static int db_cursor_open (lua_State * L) {
|
|||||||
return 2;
|
return 2;
|
||||||
}
|
}
|
||||||
static int cursor_close (lua_State * L) {
|
static int cursor_close (lua_State * L) {
|
||||||
struct rarchdb_cursor * cursor = checkcursor(L);
|
libretrodb_cursor_t *cursor = checkcursor(L);
|
||||||
rarchdb_cursor_close(cursor);
|
libretrodb_cursor_close(cursor);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -272,9 +272,9 @@ static void push_rmsgpack_value(
|
|||||||
}
|
}
|
||||||
|
|
||||||
static int cursor_read (lua_State * L) {
|
static int cursor_read (lua_State * L) {
|
||||||
struct rarchdb_cursor * cursor = checkcursor(L);
|
libretrodb_cursor_t *cursor = checkcursor(L);
|
||||||
struct rmsgpack_dom_value value;
|
struct rmsgpack_dom_value value;
|
||||||
if (rarchdb_cursor_read_item(cursor, &value) == 0) {
|
if (libretrodb_cursor_read_item(cursor, &value) == 0) {
|
||||||
push_rmsgpack_value(L, &value);
|
push_rmsgpack_value(L, &value);
|
||||||
} else {
|
} else {
|
||||||
lua_pushnil(L);
|
lua_pushnil(L);
|
||||||
@ -283,7 +283,7 @@ static int cursor_read (lua_State * L) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static int cursor_iter (lua_State * L) {
|
static int cursor_iter (lua_State * L) {
|
||||||
struct rarchdb_cursor * cursor = checkcursor(L);
|
libretrodb_cursor_t * cursor = checkcursor(L);
|
||||||
luaL_getmetafield(L, -1, "read");
|
luaL_getmetafield(L, -1, "read");
|
||||||
lua_pushvalue(L, -2);
|
lua_pushvalue(L, -2);
|
||||||
return 2;
|
return 2;
|
||||||
|
@ -33,7 +33,7 @@
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef HAVE_LIBRETRODB
|
#ifdef HAVE_LIBRETRODB
|
||||||
#include "../libretrodb/rarchdb.h"
|
#include "../libretrodb/libretrodb.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include "../input/input_remapping.h"
|
#include "../input/input_remapping.h"
|
||||||
@ -1596,8 +1596,8 @@ static int deferred_push_database_manager_list_deferred(void *data, void *userda
|
|||||||
{
|
{
|
||||||
#ifdef HAVE_LIBRETRODB
|
#ifdef HAVE_LIBRETRODB
|
||||||
int rv;
|
int rv;
|
||||||
struct rarchdb db;
|
libretrodb_t db;
|
||||||
struct rarchdb_cursor cur;
|
libretrodb_cursor_t cur;
|
||||||
struct rmsgpack_dom_value item;
|
struct rmsgpack_dom_value item;
|
||||||
#endif
|
#endif
|
||||||
unsigned i;
|
unsigned i;
|
||||||
@ -1611,13 +1611,13 @@ static int deferred_push_database_manager_list_deferred(void *data, void *userda
|
|||||||
|
|
||||||
menu_list_clear(list);
|
menu_list_clear(list);
|
||||||
#ifdef HAVE_LIBRETRODB
|
#ifdef HAVE_LIBRETRODB
|
||||||
if ((rv = rarchdb_open(path, &db)) != 0)
|
if ((rv = libretrodb_open(path, &db)) != 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if ((rv = rarchdb_cursor_open(&db, &cur, NULL)) != 0)
|
if ((rv = libretrodb_cursor_open(&db, &cur, NULL)) != 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
while (rarchdb_cursor_read_item(&cur, &item) == 0)
|
while (libretrodb_cursor_read_item(&cur, &item) == 0)
|
||||||
{
|
{
|
||||||
if (item.type != RDT_MAP)
|
if (item.type != RDT_MAP)
|
||||||
continue;
|
continue;
|
||||||
@ -1636,8 +1636,8 @@ static int deferred_push_database_manager_list_deferred(void *data, void *userda
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
rarchdb_cursor_close(&cur);
|
libretrodb_cursor_close(&cur);
|
||||||
rarchdb_close(&db);
|
libretrodb_close(&db);
|
||||||
#endif
|
#endif
|
||||||
menu_list_sort_on_alt(list);
|
menu_list_sort_on_alt(list);
|
||||||
driver.menu->scroll_indices_size = 0;
|
driver.menu->scroll_indices_size = 0;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user