diff --git a/src/vrefbuffer.c b/src/vrefbuffer.c index e03d832b..6c3ce3a0 100644 --- a/src/vrefbuffer.c +++ b/src/vrefbuffer.c @@ -25,6 +25,12 @@ bool msgpack_vrefbuffer_init(msgpack_vrefbuffer* vbuf, struct iovec* array; msgpack_vrefbuffer_chunk* chunk; + if (ref_size == 0) { + ref_size = MSGPACK_VREFBUFFER_REF_SIZE; + } + if(chunk_size == 0) { + chunk_size = MSGPACK_VREFBUFFER_CHUNK_SIZE; + } vbuf->chunk_size = chunk_size; vbuf->ref_size = ref_size > MSGPACK_PACKER_MAX_BUFFER_SIZE + 1 ? diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index c86bfc53..c902b4e6 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -8,6 +8,7 @@ INCLUDE_DIRECTORIES ( ) SET (tests_C + buffer_c.cpp fixint_c.cpp msgpack_c.cpp pack_unpack_c.cpp diff --git a/test/buffer.cpp b/test/buffer.cpp index 4e099e22..4c4000a8 100644 --- a/test/buffer.cpp +++ b/test/buffer.cpp @@ -1,8 +1,6 @@ #include #include -#include #include -#include #if defined(__GNUC__) #pragma GCC diagnostic push @@ -73,7 +71,6 @@ TEST(buffer, vrefbuffer) EXPECT_TRUE( memcmp(sbuf.data(), "aaa", 3) == 0 ); } - TEST(buffer, zbuffer) { msgpack::zbuffer zbuf; @@ -85,22 +82,6 @@ TEST(buffer, zbuffer) zbuf.flush(); } - -TEST(buffer, zbuffer_c) -{ - msgpack_zbuffer zbuf; - EXPECT_TRUE(msgpack_zbuffer_init(&zbuf, 1, MSGPACK_ZBUFFER_INIT_SIZE)); - EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "a", 1)); - EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "a", 1)); - EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "a", 1)); - EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "", 0)); - - EXPECT_TRUE(msgpack_zbuffer_flush(&zbuf) != NULL); - - msgpack_zbuffer_destroy(&zbuf); -} - - TEST(buffer, fbuffer) { #if defined(_MSC_VER) @@ -128,31 +109,3 @@ TEST(buffer, fbuffer) EXPECT_EQ(EOF, fgetc(file)); fclose(file); } - - -TEST(buffer, fbuffer_c) -{ -#if defined(_MSC_VER) - FILE* file; - tmpfile_s(&file); -#else // defined(_MSC_VER) - FILE* file = tmpfile(); -#endif // defined(_MSC_VER) - - void* fbuf = (void*)file; - - EXPECT_TRUE( file != NULL ); - EXPECT_EQ(0, msgpack_fbuffer_write(fbuf, "a", 1)); - EXPECT_EQ(0, msgpack_fbuffer_write(fbuf, "a", 1)); - EXPECT_EQ(0, msgpack_fbuffer_write(fbuf, "a", 1)); - - fflush(file); - rewind(file); - for (size_t i=0; i < 3; ++i) { - int ch = fgetc(file); - EXPECT_TRUE(ch != EOF); - EXPECT_EQ('a', (char) ch); - } - EXPECT_EQ(EOF, fgetc(file)); - fclose(file); -} diff --git a/test/buffer_c.cpp b/test/buffer_c.cpp new file mode 100644 index 00000000..01e8d24c --- /dev/null +++ b/test/buffer_c.cpp @@ -0,0 +1,148 @@ +#include +#include +#include +#include + +#if defined(__GNUC__) +#pragma GCC diagnostic push +#pragma GCC diagnostic ignored "-Wconversion" +#endif //defined(__GNUC__) + +#include + +#if defined(__GNUC__) +#pragma GCC diagnostic pop +#endif //defined(__GNUC__) + +#include + +#if defined(unix) || defined(__unix) || defined(__linux__) || defined(__APPLE__) || defined(__OpenBSD__) || defined(__NetBSD__) || defined(__QNX__) || defined(__QNXTO__) || defined(__HAIKU__) +#define HAVE_SYS_UIO_H 1 +#else +#define HAVE_SYS_UIO_H 0 +#endif + +TEST(buffer, zbuffer_c) +{ + msgpack_zbuffer zbuf; + EXPECT_TRUE(msgpack_zbuffer_init(&zbuf, 1, MSGPACK_ZBUFFER_INIT_SIZE)); + EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "a", 1)); + EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "a", 1)); + EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "a", 1)); + EXPECT_EQ(0, msgpack_zbuffer_write(&zbuf, "", 0)); + + EXPECT_TRUE(msgpack_zbuffer_flush(&zbuf) != NULL); + + msgpack_zbuffer_destroy(&zbuf); +} + +TEST(buffer, fbuffer_c) +{ +#if defined(_MSC_VER) + FILE* file; + tmpfile_s(&file); +#else // defined(_MSC_VER) + FILE* file = tmpfile(); +#endif // defined(_MSC_VER) + + void* fbuf = (void*)file; + + EXPECT_TRUE( file != NULL ); + EXPECT_EQ(0, msgpack_fbuffer_write(fbuf, "a", 1)); + EXPECT_EQ(0, msgpack_fbuffer_write(fbuf, "a", 1)); + EXPECT_EQ(0, msgpack_fbuffer_write(fbuf, "a", 1)); + + fflush(file); + rewind(file); + for (size_t i=0; i < 3; ++i) { + int ch = fgetc(file); + EXPECT_TRUE(ch != EOF); + EXPECT_EQ('a', (char) ch); + } + EXPECT_EQ(EOF, fgetc(file)); + fclose(file); +} + +TEST(buffer, sbuffer_c) +{ + msgpack_sbuffer *sbuf; + char *data; + + sbuf = msgpack_sbuffer_new(); + EXPECT_TRUE(sbuf != NULL); + EXPECT_EQ(0, msgpack_sbuffer_write(sbuf, "a", 1)); + EXPECT_EQ(0, msgpack_sbuffer_write(sbuf, "b", 1)); + EXPECT_EQ(0, msgpack_sbuffer_write(sbuf, "c", 1)); + EXPECT_EQ(0, msgpack_sbuffer_write(sbuf, "", 0)); + EXPECT_EQ(3U, sbuf->size); + EXPECT_EQ(0, memcmp(sbuf->data, "abc", 3)); + data = msgpack_sbuffer_release(sbuf); + EXPECT_EQ(0, memcmp(data, "abc", 3)); + EXPECT_EQ(0U, sbuf->size); + EXPECT_TRUE(sbuf->data == NULL); + + free(data); + msgpack_sbuffer_free(sbuf); +} + +TEST(buffer, vrefbuffer_c) +{ + const char *raw = "I was about to sail away in a junk," + "When suddenly I heard" + "The sound of stamping and singing on the bank--" + "It was you and your friends come to bid me farewell." + "The Peach Flower Lake is a thousand fathoms deep," + "But it cannot compare, O Wang Lun," + "With the depth of your love for me."; + const size_t rawlen = strlen(raw); + msgpack_vrefbuffer *vbuf; + const int ref_size = 24, chunk_size = 128; + size_t slices[] = {0, 9, 10, + MSGPACK_VREFBUFFER_REF_SIZE, + MSGPACK_VREFBUFFER_REF_SIZE + 1, + ref_size, chunk_size + 1}; + size_t iovcnt; + const iovec *iov; + size_t len = 0, i; + char *buf; + + vbuf = msgpack_vrefbuffer_new(ref_size, 0); + for (i = 0; i < sizeof(slices) / sizeof(slices[0]); i++) { + msgpack_vrefbuffer_write(vbuf, raw + len, slices[i]); + len += slices[i]; + } + EXPECT_LT(len, rawlen); + iov = msgpack_vrefbuffer_vec(vbuf); + iovcnt = msgpack_vrefbuffer_veclen(vbuf); + + buf = (char *)malloc(rawlen); +#if HAVE_SYS_UIO_H + { + int fd; + char filename[] = "/tmp/mp.XXXXXX"; + + fd = mkstemp(filename); + EXPECT_LT(0, fd); + writev(fd, iov, (int)iovcnt); + len = (size_t)lseek(fd, 0, SEEK_END); + lseek(fd, 0, SEEK_SET); + read(fd, buf, len); + EXPECT_EQ(0, memcmp(buf, raw, len)); + close(fd); + unlink(filename); + } +#else + { + len = 0; + for (i = 0; i < iovcnt; i++) + { + EXPECT_LT(len, rawlen); + memcpy(buf + len, iov[i].iov_base, iov[i].iov_len); + len += iov[i].iov_len; + } + EXPECT_EQ(0, memcmp(buf, raw, len)); + } +#endif + free(buf); + msgpack_vrefbuffer_free(vbuf); +} diff --git a/test/msgpack_c.cpp b/test/msgpack_c.cpp index 7b76a793..a2b8b921 100644 --- a/test/msgpack_c.cpp +++ b/test/msgpack_c.cpp @@ -1414,3 +1414,158 @@ TEST(MSGPACKC, object_bin_print_buffer_overflow) { EXPECT_EQ(6, ret); EXPECT_STREQ("\"test\"", buffer); } + +/* test for vrefbuffer */ +#define GEN_TEST_VREFBUFFER_PREPARE(...) \ + msgpack_vrefbuffer vbuf; \ + msgpack_packer pk; \ + const iovec *iov; \ + size_t iovcnt, len = 0, i; \ + char buf[1024]; \ + msgpack_vrefbuffer_init(&vbuf, 0, 0); \ + msgpack_packer_init(&pk, &vbuf, msgpack_vrefbuffer_write); \ + __VA_ARGS__; \ + iov = msgpack_vrefbuffer_vec(&vbuf); \ + iovcnt = msgpack_vrefbuffer_veclen(&vbuf); \ + for (i = 0; i < iovcnt; i++) { \ + memcpy(buf + len, iov[i].iov_base, iov[i].iov_len); \ + len += iov[i].iov_len; \ + } \ + msgpack_vrefbuffer_destroy(&vbuf) + +#define GEN_TEST_VREFBUFFER_CHECK(...) \ + msgpack_object obj; \ + msgpack_unpack_return ret; \ + msgpack_zone z; \ + msgpack_zone_init(&z, 2048); \ + ret = msgpack_unpack(buf, len, NULL, &z, &obj); \ + EXPECT_EQ(MSGPACK_UNPACK_SUCCESS, ret); \ + __VA_ARGS__; \ + msgpack_zone_destroy(&z) + +TEST(buffer, vrefbuffer_uint8) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_uint8(&pk, 32)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_POSITIVE_INTEGER, obj.type); + EXPECT_EQ(32U, obj.via.u64)); +} + +TEST(buffer, vrefbuffer_int8) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_int8(&pk, -32)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_NEGATIVE_INTEGER, obj.type); + EXPECT_EQ(-32, obj.via.i64)); +} + +TEST(buffer, vrefbuffer_float32) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_float(&pk, 1.0)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_FLOAT32, obj.type); + EXPECT_EQ(1.0, obj.via.f64)); +} + +TEST(buffer, vrefbuffer_float64) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_double(&pk, 1.0)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_FLOAT64, obj.type); + EXPECT_EQ(1.0, obj.via.f64)); +} + +TEST(buffer, vrefbuffer_nil) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_nil(&pk)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_NIL, obj.type)); +} + +TEST(buffer, vrefbuffer_false) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_false(&pk)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_BOOLEAN, obj.type); + EXPECT_FALSE(obj.via.boolean)); +} + +TEST(buffer, vrefbuffer_true) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_true(&pk)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_BOOLEAN, obj.type); + EXPECT_TRUE(obj.via.boolean)); +} + +#define TEST_VBUF_RAW_LEN 30U +char test_vbuf_raw[TEST_VBUF_RAW_LEN] = "frsyuki"; + +TEST(buffer, vrefbuffer_str) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_str(&pk, TEST_VBUF_RAW_LEN); + msgpack_pack_str_body(&pk, test_vbuf_raw, TEST_VBUF_RAW_LEN)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_STR, obj.type); + EXPECT_EQ(TEST_VBUF_RAW_LEN, obj.via.str.size); + EXPECT_EQ(0, memcmp(test_vbuf_raw, obj.via.str.ptr, 30))); +} + +TEST(buffer, vrefbuffer_bin) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_bin(&pk, TEST_VBUF_RAW_LEN); + msgpack_pack_bin_body(&pk, test_vbuf_raw, TEST_VBUF_RAW_LEN)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(TEST_VBUF_RAW_LEN, obj.via.bin.size); + EXPECT_EQ(0, memcmp(test_vbuf_raw, obj.via.bin.ptr, TEST_VBUF_RAW_LEN))); +} + +TEST(buffer, vrefbuffer_ext) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_ext(&pk, TEST_VBUF_RAW_LEN, 127); + msgpack_pack_ext_body(&pk, test_vbuf_raw, TEST_VBUF_RAW_LEN)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_EXT, obj.type); + EXPECT_EQ(TEST_VBUF_RAW_LEN, obj.via.ext.size); + EXPECT_EQ(0, memcmp(test_vbuf_raw, obj.via.ext.ptr, TEST_VBUF_RAW_LEN))); +} + +TEST(buffer, vrefbuffer_array) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_array(&pk, 2); + msgpack_pack_int(&pk, 3); + msgpack_pack_int(&pk, 4)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_ARRAY, obj.type); + EXPECT_EQ(2U, obj.via.array.size); + EXPECT_EQ(MSGPACK_OBJECT_POSITIVE_INTEGER, obj.via.array.ptr[0].type); + EXPECT_EQ(3U, obj.via.array.ptr[0].via.u64); + EXPECT_EQ(MSGPACK_OBJECT_POSITIVE_INTEGER, obj.via.array.ptr[1].type); + EXPECT_EQ(4U, obj.via.array.ptr[1].via.u64)); +} + +TEST(buffer, vrefbuffer_map) +{ + GEN_TEST_VREFBUFFER_PREPARE( + msgpack_pack_map(&pk, 1); + msgpack_pack_int(&pk, 2); + msgpack_pack_int(&pk, 3)); + GEN_TEST_VREFBUFFER_CHECK( + EXPECT_EQ(MSGPACK_OBJECT_MAP, obj.type); + EXPECT_EQ(1U, obj.via.map.size); + EXPECT_EQ(MSGPACK_OBJECT_POSITIVE_INTEGER, obj.via.map.ptr[0].key.type); + EXPECT_EQ(2U, obj.via.map.ptr[0].key.via.u64); + EXPECT_EQ(MSGPACK_OBJECT_POSITIVE_INTEGER, obj.via.map.ptr[0].val.type); + EXPECT_EQ(3U, obj.via.map.ptr[0].val.via.u64)); +}