Ejemplo n.º 1
0
/*
 * For each UINT key in arguments create or increment counter in
 * box.space.test space.
 */
int
multi_inc(box_function_ctx_t *ctx, const char *args, const char *args_end)
{
	static const char *SPACE_NAME = "test";
	static const char *INDEX_NAME = "primary";

	uint32_t space_id = box_space_id_by_name(SPACE_NAME, strlen(SPACE_NAME));
	uint32_t index_id = box_index_id_by_name(space_id, INDEX_NAME,
		strlen(INDEX_NAME));
	if (space_id == BOX_ID_NIL || index_id == BOX_ID_NIL) {
		return box_error_raise(ER_PROC_C,
			"Can't find index %s in space %s",
			INDEX_NAME, SPACE_NAME);
	}
	say_debug("space_id = %u, index_id = %u", space_id, index_id);

	uint32_t arg_count = mp_decode_array(&args);
	box_txn_begin();
	for (uint32_t i = 0; i < arg_count; i++) {
		/* Decode next argument */
		if (mp_typeof(*args) != MP_UINT)
			return box_error_raise(ER_PROC_C, "Expected uint keys");
		uint32_t key = mp_decode_uint(&args);
		(void) key;

		/* Prepare MsgPack key for search */
		char key_buf[16];
		char *key_end = key_buf;
		key_end = mp_encode_array(key_end, 1);
		key_end = mp_encode_uint(key_end, key);
		assert(key_end < key_buf + sizeof(key_buf));

		/* Get current value from space */
		uint64_t counter = 0;
		box_tuple_t *tuple;
		if (box_index_get(space_id, index_id, key_buf, key_end,
				  &tuple) != 0) {
			return -1; /* error */
		} else if (tuple != NULL) {
			const char *field = box_tuple_field(tuple, 1);
			if (field == NULL || mp_typeof(*field) != MP_UINT)
				return box_error_raise(ER_PROC_LUA, "Invalid tuple");
			counter = mp_decode_uint(&field) + 1;
		}

		/* Replace value */
		char tuple_buf[16];
		char *tuple_end = tuple_buf;
		tuple_end = mp_encode_array(tuple_end, 2);
		tuple_end = mp_encode_uint(tuple_end, key); /* key */
		tuple_end = mp_encode_uint(tuple_end, counter); /* counter */
		assert(tuple_end <= tuple_buf + sizeof(tuple_buf));

		if (box_replace(space_id, tuple_buf, tuple_end, NULL) != 0)
			return -1;
	}
	box_txn_commit();
	return 0;
}
Ejemplo n.º 2
0
memcached_binary_header_dump(struct memcached_hdr *hdr)
{
    if (!hdr) return;
    say_debug("memcached package");
    say_debug("magic:     0x%" PRIX8,        hdr->magic);
    say_debug("cmd:       0x%" PRIX8,        hdr->cmd);
    if (hdr->key_len > 0)
        say_debug("key_len:   %" PRIu16, mp_bswap_u16(hdr->key_len));
    if (hdr->ext_len > 0)
        say_debug("ext_len:   %" PRIu8,  hdr->ext_len);
    say_debug("tot_len:   %" PRIu32,         mp_bswap_u32(hdr->tot_len));
    say_debug("opaque:    0x%" PRIX32,       mp_bswap_u32(hdr->opaque));
    say_debug("cas:       %" PRIu64,         mp_bswap_u64(hdr->cas));
}
Ejemplo n.º 3
0
/** open file. The same as fopen but receives additional open (2) flags */
FILE *
fiob_open(const char *path, const char *mode)
{
	int omode = 0666;
	int flags = 0;
	int save_errno;
	int fd = -1;
	FILE *file = NULL;
#if defined (FIOB_DIRECT)
	struct fiob *f = NULL;
#endif /* defined(FIOB_DIRECT) */
	int um = umask(0722);
	umask(um);
	omode &= ~um;

	if (strchr(mode, 'r')) {
		if (strchr(mode, '+'))
			flags |= O_RDWR;
		else
			flags |= O_RDONLY;
	} else if (strchr(mode, 'w')) {
		flags |= O_TRUNC | O_CREAT;
		if (strchr(mode, '+'))
			flags |= O_RDWR;
		else
			flags |= O_WRONLY;
	} else if (strchr(mode, 'a')) {
		flags |= O_CREAT | O_APPEND;
		if (strchr(mode, '+'))
			flags |= O_RDWR;
		else
			flags |= O_WRONLY;
	} else {
		errno = EINVAL;
		return NULL;
	}

	/* O_EXCL */
#ifdef O_EXCL
	if (strchr(mode, 'x'))
		flags |= O_EXCL;
#endif
	/* O_SYNC */
	if (strchr(mode, 's')) {
		flags |= WAL_SYNC_FLAG;
	}

	fd = open(path, flags, omode);
	if (fd < 0)
		goto error;
#if defined(FIOB_DIRECT)
	if (strchr(mode, 'd') == NULL)
		goto fdopen;

	/* Try to enable O_DIRECT */
	flags = fcntl(fd, F_GETFL);
	if (flags != -1 && fcntl(fd, F_SETFL, flags | O_DIRECT) != -1) {
		say_debug("using O_DIRECT for %s", path);
	} else {
#if defined(NDEBUG) /* Don't use opencookie in release mode without O_DIRECT */
		goto fdopen;
#endif /* defined(NDEBUG) */
	}

	f = (struct fiob *)calloc(1, sizeof(struct fiob));
	if (!f)
		goto error;

	f->fd = fd;
	f->bsize = FIOB_BSIZE;
	if (posix_memalign(&f->buf, FIOB_ALIGN, f->bsize))
		goto error;

	/* for valgrind */
	memset(f->buf, 0, f->bsize);

	f->path = strdup(path);
	if (!f->path)
		goto error;

	f->io.read	= fiob_read;
	f->io.write	= fiob_write;
	f->io.seek	= fiob_seek;
	f->io.close	= fiob_close;

#ifdef HAVE_FUNOPEN
	file = funopen(f,
		       f->io.read, f->io.write, f->io.seek, f->io.close);
#else
	file = fopencookie(f, mode, f->io);
#endif

	if (!file)
		goto error;

#ifdef TARGET_OS_LINUX
	file->_fileno = f->fd;
#else
	file->_file = f->fd;
#endif

	return file;

fdopen:
#endif /* defined(FIOB_DIRECT) */
	/* Fallback to libc implementation */
	file = fdopen(fd, mode);
	if (!file)
		goto error;
	return file;

error:
	save_errno = errno;
	say_syserror("Can't open '%s'", path);
	if (fd >= 0)
		close(fd);

#if defined(FIOB_DIRECT)
	if (f) {
		free(f->buf);
		free(f->path);
		free(f);
	}
#endif /* FIOB_DIRECT */

	errno = save_errno;
	return NULL;
}