|
19 | 19 | */
|
20 | 20 |
|
21 | 21 | #include <fluent-bit/flb_info.h>
|
| 22 | +#include <fluent-bit/flb_utils.h> |
| 23 | +#include <fluent-bit/flb_mp.h> |
| 24 | + |
22 | 25 | #include <msgpack.h>
|
23 | 26 | #include <mpack/mpack.h>
|
24 | 27 |
|
@@ -60,3 +63,82 @@ void flb_mp_set_map_header_size(char *buf, int arr_size)
|
60 | 63 | pack_uint32(tmp, arr_size);
|
61 | 64 | }
|
62 | 65 | }
|
| 66 | + |
| 67 | +/* |
| 68 | + * msgpack-c requires to set the number of the entries in a map beforehand. For our |
| 69 | + * use case this adds some complexity, having developers to count all possible |
| 70 | + * entries that might be added. |
| 71 | + * |
| 72 | + * As a workaround and to avoid map's recomposition over and over, this simple API |
| 73 | + * allows to initialize the array header, 'register' new entries (as counters) and |
| 74 | + * finalize, upon finalization the proper array header size is adjusted. |
| 75 | + * |
| 76 | + * To make things easier, we make sure msgpack-c always register an array type of |
| 77 | + * 32 bits (identified by 0xdf, for number of entries >= 65536). Yes, for every |
| 78 | + * array using this API it will use 2 more bytes, not a big ideal. So whoever |
| 79 | + * uses this API, use it only if you don't know the exact number of entries to add. |
| 80 | + * |
| 81 | + * MANDATORY: make sure to always initialize, register every entry and finalize, |
| 82 | + * otherwise you will get a corrupted or incomplete msgpack buffer. |
| 83 | + * |
| 84 | + * Usage example |
| 85 | + * ============= |
| 86 | + * |
| 87 | + * struct flb_mp_map_head mh; |
| 88 | + * |
| 89 | + * flb_mp_map_header_init(&mh, mp_pck); |
| 90 | + * |
| 91 | + * -- First key/value entry -- |
| 92 | + * flb_mp_map_header_append(&mh); |
| 93 | + * msgpack_pack_str(mp_pck, 4); |
| 94 | + * msgpack_pack_str_body(mp_pck, "cool", 4); |
| 95 | + * msgpack_pack_true(mp_pck); |
| 96 | + * |
| 97 | + * -- Second key/value entry -- |
| 98 | + * flb_mp_map_header_append(&mh); |
| 99 | + * msgpack_pack_str(mp_pck, 4); |
| 100 | + * msgpack_pack_str_body(mp_pck, "slow", 4); |
| 101 | + * msgpack_pack_false(mp_pck); |
| 102 | + * |
| 103 | + * -- Finalize Map -- |
| 104 | + * flb_mp_map_header_end(&mh); |
| 105 | + */ |
| 106 | +int flb_mp_map_header_init(struct flb_mp_map_header *mh, msgpack_packer *mp_pck) |
| 107 | +{ |
| 108 | + msgpack_sbuffer *mp_sbuf; |
| 109 | + |
| 110 | + mp_sbuf = (msgpack_sbuffer *) mp_pck->data; |
| 111 | + |
| 112 | + /* map sbuffer */ |
| 113 | + mh->data = mp_pck->data; |
| 114 | + |
| 115 | + /* Reset entries */ |
| 116 | + mh->entries = 0; |
| 117 | + |
| 118 | + /* Store the next byte available */ |
| 119 | + mh->offset = mp_sbuf->size; |
| 120 | + |
| 121 | + /* |
| 122 | + * Pack a map with size = 65536, so we force the underlaying msgpack-c |
| 123 | + * to use a 32 bit buffer size (0xdf), reference: |
| 124 | + * |
| 125 | + * - https://github.com/msgpack/msgpack/blob/master/spec.md#map-format-family |
| 126 | + */ |
| 127 | + return msgpack_pack_map(mp_pck, 65536); |
| 128 | +} |
| 129 | + |
| 130 | +int flb_mp_map_header_append(struct flb_mp_map_header *mh) |
| 131 | +{ |
| 132 | + mh->entries++; |
| 133 | + return mh->entries; |
| 134 | +} |
| 135 | + |
| 136 | +void flb_mp_map_header_end(struct flb_mp_map_header *mh) |
| 137 | +{ |
| 138 | + char *ptr; |
| 139 | + msgpack_sbuffer *mp_sbuf; |
| 140 | + |
| 141 | + mp_sbuf = mh->data; |
| 142 | + ptr = (char *) mp_sbuf->data + mh->offset; |
| 143 | + flb_mp_set_map_header_size(ptr, mh->entries); |
| 144 | +} |
0 commit comments