diff --git a/ctdb/protocol/protocol.h b/ctdb/protocol/protocol.h index 67a66c715c1..ad757d8c27d 100644 --- a/ctdb/protocol/protocol.h +++ b/ctdb/protocol/protocol.h @@ -1007,6 +1007,15 @@ struct ctdb_g_lock_list { struct ctdb_g_lock *lock; }; +/* + * Generic packet header + */ + +struct sock_packet_header { + uint32_t length; + uint32_t reqid; +}; + /* * Eventd protocol */ diff --git a/ctdb/protocol/protocol_api.h b/ctdb/protocol/protocol_api.h index 522b009b151..22fc4483205 100644 --- a/ctdb/protocol/protocol_api.h +++ b/ctdb/protocol/protocol_api.h @@ -677,6 +677,19 @@ int ctdb_event_reply_pull(uint8_t *buf, size_t buflen, int ctdb_allocate_pkt(TALLOC_CTX *mem_ctx, size_t datalen, uint8_t **buf, size_t *buflen); +/* From protocol/protocol_sock.c */ + +size_t sock_packet_header_len(struct sock_packet_header *in); +void sock_packet_header_push(struct sock_packet_header *in, uint8_t *buf, + size_t *npush); +int sock_packet_header_pull(uint8_t *buf, size_t buflen, + struct sock_packet_header *out, size_t *npull); + +void sock_packet_header_set_reqid(struct sock_packet_header *h, + uint32_t reqid); +void sock_packet_header_set_length(struct sock_packet_header *h, + uint32_t length); + /* From protocol/protocol_util.c */ const char *ctdb_runstate_to_string(enum ctdb_runstate runstate); diff --git a/ctdb/protocol/protocol_sock.c b/ctdb/protocol/protocol_sock.c new file mode 100644 index 00000000000..e32f08767e7 --- /dev/null +++ b/ctdb/protocol/protocol_sock.c @@ -0,0 +1,81 @@ +/* + CTDB generic sock packet marshalling + + Copyright (C) Amitay Isaacs 2017 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, see . +*/ + +#include "replace.h" +#include "system/network.h" + +#include + +#include "protocol.h" +#include "protocol_private.h" +#include "protocol_api.h" + +size_t sock_packet_header_len(struct sock_packet_header *in) +{ + return ctdb_uint32_len(&in->length) + + ctdb_uint32_len(&in->reqid); +} + +void sock_packet_header_push(struct sock_packet_header *in, uint8_t *buf, + size_t *npush) +{ + size_t offset = 0, np; + + ctdb_uint32_push(&in->length, buf+offset, &np); + offset += np; + + ctdb_uint32_push(&in->reqid, buf+offset, &np); + offset += np; + + *npush = offset; +} + +int sock_packet_header_pull(uint8_t *buf, size_t buflen, + struct sock_packet_header *out, size_t *npull) +{ + size_t offset = 0, np; + int ret; + + ret = ctdb_uint32_pull(buf+offset, buflen-offset, &out->length, &np); + if (ret != 0) { + return ret; + } + offset += np; + + ret = ctdb_uint32_pull(buf+offset, buflen-offset, &out->reqid, &np); + if (ret != 0) { + return ret; + } + offset += np; + + *npull = offset; + return 0; +} + +void sock_packet_header_set_reqid(struct sock_packet_header *h, + uint32_t reqid) +{ + h->reqid = reqid; +} + +void sock_packet_header_set_length(struct sock_packet_header *h, + uint32_t length) +{ + h->length = length; +} diff --git a/ctdb/tests/src/protocol_common.c b/ctdb/tests/src/protocol_common.c index f5fe3c7901b..e9ba658259c 100644 --- a/ctdb/tests/src/protocol_common.c +++ b/ctdb/tests/src/protocol_common.c @@ -1383,3 +1383,16 @@ void verify_ctdb_g_lock_list(struct ctdb_g_lock_list *p1, verify_ctdb_g_lock(&p1->lock[i], &p2->lock[i]); } } + +void fill_sock_packet_header(struct sock_packet_header *p) +{ + p->length = rand32(); + p->reqid = rand32(); +} + +void verify_sock_packet_header(struct sock_packet_header *p1, + struct sock_packet_header *p2) +{ + assert(p1->length == p2->length); + assert(p1->reqid == p2->reqid); +} diff --git a/ctdb/tests/src/protocol_common.h b/ctdb/tests/src/protocol_common.h index 5a270328b5f..01b1e34a440 100644 --- a/ctdb/tests/src/protocol_common.h +++ b/ctdb/tests/src/protocol_common.h @@ -350,4 +350,8 @@ void fill_ctdb_g_lock_list(TALLOC_CTX *mem_ctx, struct ctdb_g_lock_list *p); void verify_ctdb_g_lock_list(struct ctdb_g_lock_list *p1, struct ctdb_g_lock_list *p2); +void fill_sock_packet_header(struct sock_packet_header *p); +void verify_sock_packet_header(struct sock_packet_header *p1, + struct sock_packet_header *p2); + #endif /* __CTDB_PROTOCOL_COMMON_H__ */ diff --git a/ctdb/tests/src/protocol_types_test.c b/ctdb/tests/src/protocol_types_test.c index 15ccd49999f..7dbc99edfc6 100644 --- a/ctdb/tests/src/protocol_types_test.c +++ b/ctdb/tests/src/protocol_types_test.c @@ -24,6 +24,7 @@ #include "protocol/protocol_basic.c" #include "protocol/protocol_types.c" +#include "protocol/protocol_sock.c" #include "tests/src/protocol_common.h" @@ -75,6 +76,8 @@ PROTOCOL_TYPE1_TEST(struct ctdb_server_id, ctdb_server_id); PROTOCOL_TYPE1_TEST(struct ctdb_g_lock, ctdb_g_lock); PROTOCOL_TYPE3_TEST(struct ctdb_g_lock_list, ctdb_g_lock_list); +PROTOCOL_TYPE1_TEST(struct sock_packet_header, sock_packet_header); + static void test_ctdb_rec_buffer_read_write(void) { TALLOC_CTX *mem_ctx = talloc_new(NULL); @@ -176,6 +179,8 @@ int main(int argc, char *argv[]) TEST_FUNC(ctdb_g_lock)(); TEST_FUNC(ctdb_g_lock_list)(); + TEST_FUNC(sock_packet_header)(); + test_ctdb_rec_buffer_read_write(); return 0; diff --git a/ctdb/wscript b/ctdb/wscript index a35b138eba4..2a686d08424 100644 --- a/ctdb/wscript +++ b/ctdb/wscript @@ -400,7 +400,8 @@ def build(bld): protocol_client.c protocol_debug.c protocol_util.c - protocol_event.c'''), + protocol_event.c + protocol_sock.c'''), includes='include', deps='replace talloc tdb')