mirror of
https://github.com/msgpack/msgpack-c.git
synced 2025-07-04 01:27:13 +02:00
Merge pull request #707 from redboltz/ts_c
Added timestamp minimal support for C.
This commit is contained in:
commit
5bd75905cb
@ -142,6 +142,7 @@ LIST (APPEND msgpackc_HEADERS
|
||||
include/msgpack/predef/version_number.h
|
||||
include/msgpack/sbuffer.h
|
||||
include/msgpack/sysdep.h
|
||||
include/msgpack/timestamp.h
|
||||
include/msgpack/unpack.h
|
||||
include/msgpack/unpack_define.h
|
||||
include/msgpack/unpack_template.h
|
||||
|
@ -12,6 +12,7 @@
|
||||
|
||||
#include "pack_define.h"
|
||||
#include "object.h"
|
||||
#include "timestamp.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
@ -98,6 +99,8 @@ static int msgpack_pack_bin_body(msgpack_packer* pk, const void* b, size_t l);
|
||||
static int msgpack_pack_ext(msgpack_packer* pk, size_t l, int8_t type);
|
||||
static int msgpack_pack_ext_body(msgpack_packer* pk, const void* b, size_t l);
|
||||
|
||||
static int msgpack_pack_timestamp(msgpack_packer* pk, const msgpack_timestamp* d);
|
||||
|
||||
MSGPACK_DLLEXPORT
|
||||
int msgpack_pack_object(msgpack_packer* pk, msgpack_object d);
|
||||
|
||||
|
@ -890,6 +890,34 @@ msgpack_pack_inline_func(_ext_body)(msgpack_pack_user x, const void* b, size_t l
|
||||
msgpack_pack_append_buffer(x, (const unsigned char*)b, l);
|
||||
}
|
||||
|
||||
msgpack_pack_inline_func(_timestamp)(msgpack_pack_user x, const msgpack_timestamp* d)
|
||||
{
|
||||
if ((((int64_t)d->tv_sec) >> 34) == 0) {
|
||||
uint64_t data64 = ((uint64_t) d->tv_nsec << 34) | d->tv_sec;
|
||||
if ((data64 & 0xffffffff00000000L) == 0) {
|
||||
// timestamp 32
|
||||
char buf[4];
|
||||
uint32_t data32 = (uint32_t)data64;
|
||||
msgpack_pack_ext(x, 4, -1);
|
||||
_msgpack_store32(buf, data32);
|
||||
msgpack_pack_append_buffer(x, buf, 4);
|
||||
} else {
|
||||
// timestamp 64
|
||||
char buf[8];
|
||||
msgpack_pack_ext(x, 8, -1);
|
||||
_msgpack_store64(buf, data64);
|
||||
msgpack_pack_append_buffer(x, buf, 8);
|
||||
}
|
||||
} else {
|
||||
// timestamp 96
|
||||
char buf[12];
|
||||
_msgpack_store32(&buf[0], d->tv_nsec);
|
||||
_msgpack_store64(&buf[4], d->tv_sec);
|
||||
msgpack_pack_ext(x, 12, -1);
|
||||
msgpack_pack_append_buffer(x, buf, 12);
|
||||
}
|
||||
}
|
||||
|
||||
#undef msgpack_pack_inline_func
|
||||
#undef msgpack_pack_user
|
||||
#undef msgpack_pack_append_buffer
|
||||
|
54
include/msgpack/timestamp.h
Normal file
54
include/msgpack/timestamp.h
Normal file
@ -0,0 +1,54 @@
|
||||
/*
|
||||
* MessagePack for C TimeStamp
|
||||
*
|
||||
* Copyright (C) 2018 KONDO Takatoshi
|
||||
*
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
#ifndef MSGPACK_TIMESTAMP_H
|
||||
#define MSGPACK_TIMESTAMP_H
|
||||
|
||||
#include <msgpack/object.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
typedef struct msgpack_timestamp {
|
||||
int64_t tv_sec;
|
||||
uint32_t tv_nsec;
|
||||
} msgpack_timestamp;
|
||||
|
||||
static inline bool msgpack_object_to_timestamp(const msgpack_object* obj, msgpack_timestamp* ts) {
|
||||
if (obj->type != MSGPACK_OBJECT_EXT) return false;
|
||||
if (obj->via.ext.type != -1) return false;
|
||||
switch (obj->via.ext.size) {
|
||||
case 4:
|
||||
ts->tv_nsec = 0;
|
||||
_msgpack_load32(uint32_t, obj->via.ext.ptr, &ts->tv_sec);
|
||||
return true;
|
||||
case 8: {
|
||||
uint64_t value;
|
||||
_msgpack_load64(uint64_t, obj->via.ext.ptr, &value);
|
||||
ts->tv_nsec = (uint32_t)(value >> 34);
|
||||
ts->tv_sec = value & 0x00000003ffffffffL;
|
||||
return true;
|
||||
}
|
||||
case 12:
|
||||
_msgpack_load32(uint32_t, obj->via.ext.ptr, &ts->tv_nsec);
|
||||
_msgpack_load64(int64_t, obj->via.ext.ptr + 4, &ts->tv_sec);
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* msgpack/timestamp.h */
|
@ -627,6 +627,105 @@ TEST(MSGPACKC, simple_buffer_fixext_4byte_65536)
|
||||
msgpack_sbuffer_destroy(&sbuf);
|
||||
}
|
||||
|
||||
TEST(MSGPACKC, simple_buffer_timestamp_32)
|
||||
{
|
||||
msgpack_timestamp ts = {
|
||||
0xffffffff,
|
||||
0
|
||||
};
|
||||
|
||||
msgpack_sbuffer sbuf;
|
||||
msgpack_sbuffer_init(&sbuf);
|
||||
msgpack_packer pk;
|
||||
msgpack_packer_init(&pk, &sbuf, msgpack_sbuffer_write);
|
||||
|
||||
msgpack_pack_timestamp(&pk, &ts);
|
||||
msgpack_zone z;
|
||||
msgpack_zone_init(&z, 2048);
|
||||
msgpack_object obj;
|
||||
msgpack_unpack_return ret =
|
||||
msgpack_unpack(sbuf.data, sbuf.size, NULL, &z, &obj);
|
||||
EXPECT_EQ(MSGPACK_UNPACK_SUCCESS, ret);
|
||||
EXPECT_EQ(MSGPACK_OBJECT_EXT, obj.type);
|
||||
EXPECT_EQ(4u, obj.via.ext.size);
|
||||
EXPECT_EQ(-1, obj.via.ext.type);
|
||||
msgpack_timestamp ts2;
|
||||
bool r = msgpack_object_to_timestamp(&obj, &ts2);
|
||||
|
||||
EXPECT_TRUE(r);
|
||||
EXPECT_EQ(ts.tv_sec, ts2.tv_sec);
|
||||
EXPECT_EQ(ts.tv_nsec, ts2.tv_nsec);
|
||||
|
||||
msgpack_zone_destroy(&z);
|
||||
msgpack_sbuffer_destroy(&sbuf);
|
||||
}
|
||||
|
||||
TEST(MSGPACKC, simple_buffer_timestamp_64)
|
||||
{
|
||||
msgpack_timestamp ts = {
|
||||
0x3ffffffffL,
|
||||
999999999
|
||||
};
|
||||
|
||||
msgpack_sbuffer sbuf;
|
||||
msgpack_sbuffer_init(&sbuf);
|
||||
msgpack_packer pk;
|
||||
msgpack_packer_init(&pk, &sbuf, msgpack_sbuffer_write);
|
||||
|
||||
msgpack_pack_timestamp(&pk, &ts);
|
||||
msgpack_zone z;
|
||||
msgpack_zone_init(&z, 2048);
|
||||
msgpack_object obj;
|
||||
msgpack_unpack_return ret =
|
||||
msgpack_unpack(sbuf.data, sbuf.size, NULL, &z, &obj);
|
||||
EXPECT_EQ(MSGPACK_UNPACK_SUCCESS, ret);
|
||||
EXPECT_EQ(MSGPACK_OBJECT_EXT, obj.type);
|
||||
EXPECT_EQ(8u, obj.via.ext.size);
|
||||
EXPECT_EQ(-1, obj.via.ext.type);
|
||||
msgpack_timestamp ts2;
|
||||
bool r = msgpack_object_to_timestamp(&obj, &ts2);
|
||||
|
||||
EXPECT_TRUE(r);
|
||||
EXPECT_EQ(ts.tv_sec, ts2.tv_sec);
|
||||
EXPECT_EQ(ts.tv_nsec, ts2.tv_nsec);
|
||||
|
||||
msgpack_zone_destroy(&z);
|
||||
msgpack_sbuffer_destroy(&sbuf);
|
||||
}
|
||||
|
||||
TEST(MSGPACKC, simple_buffer_timestamp_96)
|
||||
{
|
||||
msgpack_timestamp ts = {
|
||||
0x7fffffffffffffffLL,
|
||||
999999999
|
||||
};
|
||||
|
||||
msgpack_sbuffer sbuf;
|
||||
msgpack_sbuffer_init(&sbuf);
|
||||
msgpack_packer pk;
|
||||
msgpack_packer_init(&pk, &sbuf, msgpack_sbuffer_write);
|
||||
|
||||
msgpack_pack_timestamp(&pk, &ts);
|
||||
msgpack_zone z;
|
||||
msgpack_zone_init(&z, 2048);
|
||||
msgpack_object obj;
|
||||
msgpack_unpack_return ret =
|
||||
msgpack_unpack(sbuf.data, sbuf.size, NULL, &z, &obj);
|
||||
EXPECT_EQ(MSGPACK_UNPACK_SUCCESS, ret);
|
||||
EXPECT_EQ(MSGPACK_OBJECT_EXT, obj.type);
|
||||
EXPECT_EQ(12u, obj.via.ext.size);
|
||||
EXPECT_EQ(-1, obj.via.ext.type);
|
||||
msgpack_timestamp ts2;
|
||||
bool r = msgpack_object_to_timestamp(&obj, &ts2);
|
||||
|
||||
EXPECT_TRUE(r);
|
||||
EXPECT_EQ(ts.tv_sec, ts2.tv_sec);
|
||||
EXPECT_EQ(ts.tv_nsec, ts2.tv_nsec);
|
||||
|
||||
msgpack_zone_destroy(&z);
|
||||
msgpack_sbuffer_destroy(&sbuf);
|
||||
}
|
||||
|
||||
TEST(MSGPACKC, simple_buffer_array)
|
||||
{
|
||||
unsigned int array_size = 5;
|
||||
|
Loading…
x
Reference in New Issue
Block a user