X-Git-Url: https://git.lttng.org/?a=blobdiff_plain;f=src%2Flib%2Fmsgpack%2Fmsgpack.c;h=54d5692679cd926fec304dc4bff0821142e6197e;hb=95ab0b458d258f604de7a1ef387e4be0d1c7ceb5;hp=16658d11b7843aaebe995126367e05d88ad8edd5;hpb=caf6ac496bf11139aefc46a69d2913e7f7222733;p=lttng-modules.git diff --git a/src/lib/msgpack/msgpack.c b/src/lib/msgpack/msgpack.c index 16658d11..54d56926 100644 --- a/src/lib/msgpack/msgpack.c +++ b/src/lib/msgpack/msgpack.c @@ -20,7 +20,6 @@ #define _GNU_SOURCE #define _LGPL_SOURCE -#include #define MSGPACK_FIXSTR_ID_MASK 0xA0 #define MSGPACK_FIXMAP_ID_MASK 0x80 @@ -58,6 +57,7 @@ #include #include +#include #define INT8_MIN (-128) #define INT16_MIN (-32767-1) @@ -114,6 +114,30 @@ end: return ret; } +static inline int lttng_msgpack_append_user_buffer( + struct lttng_msgpack_writer *writer, + const uint8_t __user *ubuf, + size_t length) +{ + int ret = 0; + + lttng_msgpack_assert(ubuf); + + /* Ensure we are not trying to write after the end of the buffer. */ + if (writer->write_pos + length > writer->end_write_pos) { + ret = -1; + goto end; + } + + if (lttng_copy_from_user_check_nofault(writer->write_pos, ubuf, length)) { + ret = -1; + goto end; + } + writer->write_pos += length; +end: + return ret; +} + static inline int lttng_msgpack_append_u8( struct lttng_msgpack_writer *writer, uint8_t value) { @@ -144,20 +168,6 @@ static inline int lttng_msgpack_append_u64( return lttng_msgpack_append_buffer(writer, (uint8_t *) &value, sizeof(value)); } -static inline int lttng_msgpack_append_f64( - struct lttng_msgpack_writer *writer, double value) -{ - - union { - double d; - uint64_t u; - } u; - - u.d = value; - - return lttng_msgpack_append_u64(writer, u.u); -} - static inline int lttng_msgpack_append_i8( struct lttng_msgpack_writer *writer, int8_t value) { @@ -182,23 +192,6 @@ static inline int lttng_msgpack_append_i64( return lttng_msgpack_append_u64(writer, (uint64_t) value); } -static inline int lttng_msgpack_encode_f64( - struct lttng_msgpack_writer *writer, double value) -{ - int ret; - - ret = lttng_msgpack_append_u8(writer, MSGPACK_FLOAT64_ID); - if (ret) - goto end; - - ret = lttng_msgpack_append_f64(writer, value); - if (ret) - goto end; - -end: - return ret; -} - static inline int lttng_msgpack_encode_fixmap( struct lttng_msgpack_writer *writer, uint8_t count) { @@ -313,6 +306,53 @@ end: return ret; } +static inline int lttng_msgpack_encode_user_fixstr( + struct lttng_msgpack_writer *writer, + const char __user *ustr, + uint8_t len) +{ + int ret; + + lttng_msgpack_assert(len <= MSGPACK_FIXSTR_MAX_LENGTH); + + ret = lttng_msgpack_append_u8(writer, MSGPACK_FIXSTR_ID_MASK | len); + if (ret) + goto end; + + ret = lttng_msgpack_append_user_buffer(writer, (uint8_t __user *) ustr, len); + if (ret) + goto end; + +end: + return ret; +} + +static inline int lttng_msgpack_encode_user_str16( + struct lttng_msgpack_writer *writer, + const char __user *ustr, + uint16_t len) +{ + int ret; + + lttng_msgpack_assert(len > MSGPACK_FIXSTR_MAX_LENGTH); + + ret = lttng_msgpack_append_u8(writer, MSGPACK_STR16_ID); + if (ret) + goto end; + + ret = lttng_msgpack_append_u16(writer, len); + if (ret) + goto end; + + ret = lttng_msgpack_append_user_buffer(writer, (uint8_t __user *) ustr, len); + if (ret) + goto end; + +end: + return ret; +} + + int lttng_msgpack_begin_map(struct lttng_msgpack_writer *writer, size_t count) { int ret; @@ -386,6 +426,30 @@ end: return ret; } +/* + * Provide the same behavior on lttng_strlen_user_inatomic page fault as the + * lttng ring buffer: truncate the last string character. + */ +int lttng_msgpack_write_user_str(struct lttng_msgpack_writer *writer, + const char __user *ustr) +{ + int ret; + size_t length = max_t(size_t, lttng_strlen_user_inatomic(ustr), 1); + + if (length >= (1 << 16)) { + ret = -1; + goto end; + } + + if (length <= MSGPACK_FIXSTR_MAX_LENGTH) + ret = lttng_msgpack_encode_user_fixstr(writer, ustr, length); + else + ret = lttng_msgpack_encode_user_str16(writer, ustr, length); + +end: + return ret; +} + int lttng_msgpack_write_nil(struct lttng_msgpack_writer *writer) { return lttng_msgpack_append_u8(writer, MSGPACK_NIL_ID); @@ -494,9 +558,16 @@ end: return ret; } -int lttng_msgpack_write_double(struct lttng_msgpack_writer *writer, double value) +int lttng_msgpack_save_writer_pos(struct lttng_msgpack_writer *writer, uint8_t **pos) +{ + *pos = writer->write_pos; + return 0; +} + +int lttng_msgpack_restore_writer_pos(struct lttng_msgpack_writer *writer, uint8_t *pos) { - return lttng_msgpack_encode_f64(writer, value); + writer->write_pos = pos; + return 0; } void lttng_msgpack_writer_init(struct lttng_msgpack_writer *writer,