From f49bf6686419da91038661a1f1ff40160319c1e4 Mon Sep 17 00:00:00 2001 From: Jennifer Richards Date: Wed, 15 Jun 2016 12:17:17 -0400 Subject: [PATCH] Encode route_req messages. --- include/trp_internal.h | 13 ++-- trp/msgtst.c | 8 ++- trp/trp_msg.c | 192 ++++++++++++++++++++++++++++++++++++------------- 3 files changed, 155 insertions(+), 58 deletions(-) diff --git a/include/trp_internal.h b/include/trp_internal.h index 3f081cf..cc65efc 100644 --- a/include/trp_internal.h +++ b/include/trp_internal.h @@ -42,7 +42,7 @@ typedef struct trp_msg_info_route TRP_MSG_INFO_ROUTE; struct trp_msg_info_route { void *next; TRP_MSG_INFO_TYPE type; - TR_NAME *community; + TR_NAME *comm; TR_NAME *realm; TR_NAME *trust_router; unsigned int metric; @@ -51,14 +51,14 @@ struct trp_msg_info_route { /* TODO: define struct trp_msg_info_community */ -typedef struct trp_msg_body_update { +typedef struct trp_route_update { void *records; -} TRP_MSG_BODY_UPDATE; +} TRP_ROUTE_UPDATE; -typedef struct trp_msg_body_route_req { - TR_NAME *community; +typedef struct trp_route_req { + TR_NAME *comm; TR_NAME *realm; -} TRP_MSG_BODY_ROUTE_REQ; +} TRP_ROUTE_REQ; TRP_MSG_TYPE trp_msg_type_from_string(const char *s); const char *trp_msg_type_to_string(TRP_MSG_TYPE msgtype); @@ -68,6 +68,7 @@ const char *trp_msg_info_type_to_string(TRP_MSG_INFO_TYPE msgtype); TRP_MSG *trp_msg_new(TALLOC_CTX *mem_ctx); void trp_msg_destroy(TRP_MSG *msg); void trp_msg_pprint(TRP_MSG *msg); +char *trp_encode_msg(TRP_MSG *msg); typedef struct trps_instance TRPS_INSTANCE; diff --git a/trp/msgtst.c b/trp/msgtst.c index 2b73eb3..5622e3a 100644 --- a/trp/msgtst.c +++ b/trp/msgtst.c @@ -53,11 +53,15 @@ int main(int argc, const char *argv[]) if (rc==TRP_SUCCESS) trp_msg_print(msg); - talloc_report_full(main_ctx, stderr); + printf("\nEncoding...\n"); + + printf("Result: \n%s\n\n", trp_encode_msg(msg)); + + talloc_report_full(main_ctx, stdout); if (rc==TRP_SUCCESS) talloc_free(msg); - talloc_report_full(main_ctx, stderr); + talloc_report_full(main_ctx, stdout); return 0; } diff --git a/trp/trp_msg.c b/trp/trp_msg.c index ea90cf1..10f15f5 100644 --- a/trp/trp_msg.c +++ b/trp/trp_msg.c @@ -1,3 +1,4 @@ +#include #include #include @@ -6,13 +7,14 @@ /* static prototypes */ -static void *trp_msg_body_update_new(TALLOC_CTX *mem_ctx); +static void *trp_route_update_new(TALLOC_CTX *mem_ctx); static TRP_RC trp_parse_update(TRP_MSG *msg, json_t *jmsg); -static void trp_msg_body_update_print(void *); +static void trp_route_update_print(void *); -static void *trp_msg_body_route_req_new(TALLOC_CTX *mem_ctx); +static void *trp_route_req_new(TALLOC_CTX *mem_ctx); +static json_t *trp_encode_route_req(void *req_in); static TRP_RC trp_parse_route_req(TRP_MSG *msg, json_t *jmsg); -static void trp_msg_body_route_req_print(void *); +static void trp_route_req_print(void *); static void *trp_msg_info_route_new(TALLOC_CTX *mem_ctx); static TRP_RC trp_parse_info_route(TRP_MSG *msg, json_t *jmsg); @@ -22,20 +24,21 @@ static void trp_msg_info_route_print(void *); struct trp_msg_type_entry { const char *name; TRP_MSG_TYPE type; - void *(*allocator)(TALLOC_CTX *); - TRP_RC (*parser)(TRP_MSG *, json_t *); - void (*printer)(void *); + void *(*allocate)(TALLOC_CTX *); + json_t *(*encode)(void *); + TRP_RC (*parse)(TRP_MSG *, json_t *); + void (*print)(void *); }; static struct trp_msg_type_entry trp_msg_type_table[] = { - { "update", TRP_MSG_TYPE_UPDATE, trp_msg_body_update_new, trp_parse_update, trp_msg_body_update_print }, - { "route_req", TRP_MSG_TYPE_ROUTE_REQ, trp_msg_body_route_req_new, trp_parse_route_req, trp_msg_body_route_req_print }, - { NULL, TRP_MSG_TYPE_UNKNOWN, NULL, NULL, NULL } /* must be the last entry */ + { "update", TRP_MSG_TYPE_UPDATE, trp_route_update_new, NULL, trp_parse_update, trp_route_update_print }, + { "route_req", TRP_MSG_TYPE_ROUTE_REQ, trp_route_req_new, trp_encode_route_req, trp_parse_route_req, trp_route_req_print }, + { NULL, TRP_MSG_TYPE_UNKNOWN, NULL, NULL, NULL, NULL } /* must be the last entry */ }; struct trp_msg_info_type_entry { const char *name; TRP_MSG_INFO_TYPE type; - void (*printer)(void *); + void (*print)(void *); }; static struct trp_msg_info_type_entry trp_msg_info_type_table[] = { { "route_info", TRP_MSG_INFO_TYPE_ROUTE, trp_msg_info_route_print }, @@ -50,11 +53,11 @@ static void msg_body_type_check(TRP_MSG_TYPE msgtype, void *p) { switch (msgtype) { case TRP_MSG_TYPE_UPDATE: - talloc_get_type_abort(p, TRP_MSG_BODY_UPDATE); + talloc_get_type_abort(p, TRP_ROUTE_UPDATE); break; case TRP_MSG_TYPE_ROUTE_REQ: - talloc_get_type_abort(p, TRP_MSG_BODY_ROUTE_REQ); + talloc_get_type_abort(p, TRP_ROUTE_REQ); break; default: @@ -192,9 +195,9 @@ static int trp_msg_info_route_destructor(void *object) TRP_MSG_INFO_ROUTE *body=talloc_get_type_abort(object, TRP_MSG_INFO_ROUTE); /* clean up TR_NAME data, which are not managed by talloc */ - if (body->community != NULL) { - tr_free_name(body->community); - body->community=NULL; + if (body->comm != NULL) { + tr_free_name(body->comm); + body->comm=NULL; tr_debug("trp_msg_info_route_destructor: freed community"); } if (body->realm != NULL) { @@ -218,7 +221,7 @@ static void *trp_msg_info_route_new(TALLOC_CTX *mem_ctx) if (new_rec != NULL) { new_rec->next=NULL; new_rec->type=TRP_MSG_INFO_TYPE_UNKNOWN; - new_rec->community=NULL; + new_rec->comm=NULL; new_rec->realm=NULL; new_rec->trust_router=NULL; new_rec->metric=TRP_METRIC_INFINITY; @@ -252,11 +255,11 @@ static TRP_RC trp_parse_update_record(TRP_MSG_INFO_ROUTE *rec, json_t *jrecord) rc=trp_get_json_string(jrecord, "community", &s, tmp_ctx); if (rc != TRP_SUCCESS) goto cleanup; - if (NULL==(rec->community=tr_new_name(s))) + if (NULL==(rec->comm=tr_new_name(s))) goto cleanup; talloc_free(s); s=NULL; - tr_debug("trp_parse_update_record: 'community' is '%.*s'.", rec->community->len, rec->community->buf); + tr_debug("trp_parse_update_record: 'community' is '%.*s'.", rec->comm->len, rec->comm->buf); rc=trp_get_json_string(jrecord, "realm", &s, tmp_ctx); if (rc != TRP_SUCCESS) @@ -295,9 +298,9 @@ static TRP_RC trp_parse_update_record(TRP_MSG_INFO_ROUTE *rec, json_t *jrecord) cleanup: if (rc != TRP_SUCCESS) { /* clean up TR_NAME data, which is not managed by talloc */ - if (rec->community != NULL) { - tr_free_name(rec->community); - rec->community=NULL; + if (rec->comm != NULL) { + tr_free_name(rec->comm); + rec->comm=NULL; } if (rec->realm != NULL) { tr_free_name(rec->realm); @@ -315,9 +318,9 @@ cleanup: -static void *trp_msg_body_update_new(TALLOC_CTX *mem_ctx) +static void *trp_route_update_new(TALLOC_CTX *mem_ctx) { - TRP_MSG_BODY_UPDATE *new_body=talloc(mem_ctx, TRP_MSG_BODY_UPDATE); + TRP_ROUTE_UPDATE *new_body=talloc(mem_ctx, TRP_ROUTE_UPDATE); if (new_body!=NULL) { new_body->records=NULL; @@ -328,14 +331,15 @@ static void *trp_msg_body_update_new(TALLOC_CTX *mem_ctx) * * An error will be returned if any unparseable records are encountered. * - * TODO: clean up return codes. */ + * TODO: clean up return codes. + * TODO: should take a body, not a msg */ static TRP_RC trp_parse_update(TRP_MSG *msg, json_t *jbody) { TALLOC_CTX *tmp_ctx=talloc_new(NULL); json_t *jrecords=NULL; size_t ii=0; size_t nrec=0; - TRP_MSG_BODY_UPDATE *msg_body=NULL; + TRP_ROUTE_UPDATE *msg_body=NULL; TRP_MSG_INFO_ROUTE *new_rec=NULL; TRP_MSG_INFO_ROUTE *list_tail=NULL; TRP_RC rc=TRP_ERROR; @@ -344,7 +348,7 @@ static TRP_RC trp_parse_update(TRP_MSG *msg, json_t *jbody) rc=TRP_BADTYPE; goto cleanup; } - msg_body=talloc_get_type(msg->body, TRP_MSG_BODY_UPDATE); + msg_body=talloc_get_type(msg->body, TRP_ROUTE_UPDATE); if (msg_body==NULL) { rc=TRP_BADTYPE; goto cleanup; @@ -400,7 +404,7 @@ static void trp_msg_info_route_print(void *rec_in) while (rec!=NULL) { printf(" [record_type=%s\n community=%.*s\n realm=%.*s\n trust_router=%.*s\n metric=%d\n interval=%d]\n", trp_msg_info_type_to_string(rec->type), - rec->community->len, rec->community->buf, + rec->comm->len, rec->comm->buf, rec->realm->len, rec->realm->buf, rec->trust_router->len, rec->trust_router->buf, rec->metric, rec->interval); @@ -409,40 +413,53 @@ static void trp_msg_info_route_print(void *rec_in) } -static int trp_msg_body_route_req_destructor(void *object) +static int trp_route_req_destructor(void *object) { - TRP_MSG_BODY_ROUTE_REQ *body=talloc_get_type_abort(object, TRP_MSG_BODY_ROUTE_REQ); + TRP_ROUTE_REQ *body=talloc_get_type_abort(object, TRP_ROUTE_REQ); /* clean up TR_NAME data, which are not managed by talloc */ - if (body->community != NULL) { - tr_free_name(body->community); - body->community=NULL; - tr_debug("trp_msg_body_route_req_destructor: freed community"); + if (body->comm != NULL) { + tr_free_name(body->comm); + body->comm=NULL; + tr_debug("trp_route_req_destructor: freed community"); } if (body->realm != NULL) { tr_free_name(body->realm); body->realm=NULL; - tr_debug("trp_msg_body_route_req_destructor: freed realm"); + tr_debug("trp_route_req_destructor: freed realm"); } return 0; } -static void *trp_msg_body_route_req_new(TALLOC_CTX *mem_ctx) + +void *trp_route_req_new(TALLOC_CTX *mem_ctx) { - TRP_MSG_BODY_ROUTE_REQ *new_body=talloc(mem_ctx, TRP_MSG_BODY_ROUTE_REQ); + TRP_ROUTE_REQ *new_body=talloc(mem_ctx, TRP_ROUTE_REQ); if (new_body != NULL) { - new_body->community=NULL; + new_body->comm=NULL; new_body->realm=NULL; } - talloc_set_destructor((void *)new_body, trp_msg_body_route_req_destructor); + talloc_set_destructor((void *)new_body, trp_route_req_destructor); return new_body; } +void trp_route_req_set_comm(TRP_ROUTE_REQ *req, TR_NAME *comm) +{ + req->comm=comm; +} + +void trp_route_req_set_realm(TRP_ROUTE_REQ *req, TR_NAME *realm) +{ + req->realm=realm; +} + +/* TODO: clean up return codes. + * TODO: should take a body, not a msg */ static TRP_RC trp_parse_route_req(TRP_MSG *msg, json_t *jbody) { TALLOC_CTX *tmp_ctx=talloc_new(NULL); - TRP_MSG_BODY_ROUTE_REQ *msg_body=NULL; + TRP_ROUTE_REQ *msg_body=NULL; char *s=NULL; TRP_RC rc=TRP_ERROR; @@ -451,7 +468,7 @@ static TRP_RC trp_parse_route_req(TRP_MSG *msg, json_t *jbody) rc=TRP_BADTYPE; goto cleanup; } - msg_body=talloc_get_type(msg->body, TRP_MSG_BODY_ROUTE_REQ); + msg_body=talloc_get_type(msg->body, TRP_ROUTE_REQ); if (msg_body==NULL) { rc=TRP_BADTYPE; goto cleanup; @@ -460,7 +477,7 @@ static TRP_RC trp_parse_route_req(TRP_MSG *msg, json_t *jbody) rc=trp_get_json_string(jbody, "community", &s, tmp_ctx); if (rc!=TRP_SUCCESS) goto cleanup; - msg_body->community=tr_new_name(s); + msg_body->comm=tr_new_name(s); talloc_free(s); s=NULL; rc=trp_get_json_string(jbody, "realm", &s, tmp_ctx); @@ -475,9 +492,84 @@ cleanup: return rc; } -static void trp_msg_body_update_print(void *body_in) +static json_t *trp_encode_body(TRP_MSG_TYPE type, void *body) +{ + struct trp_msg_type_entry *msgtype=get_trp_msg_type_entry(type); + + if ((msgtype->type==TRP_MSG_TYPE_UNKNOWN) || (msgtype->encode==NULL)) + return NULL; + + tr_debug("trp_encode_body: encoding type %s", trp_msg_type_to_string(type)); + + return msgtype->encode(body); +} + +/* TODO: error checking */ +char *trp_encode_msg(TRP_MSG *msg) +{ + json_t *jmsg=NULL; + json_t *jtype=NULL; + json_t *jbody=NULL; + char *encoded=NULL; + + jbody=trp_encode_body(msg->type, msg->body); + if (jbody!=NULL) { + jmsg=json_object(); + + jtype=json_string(trp_msg_type_to_string(msg->type)); + json_object_set_new(jmsg, "message_type", jtype); + json_object_set_new(jmsg, "body", jbody); + + encoded=json_dumps(jmsg, 0); + json_decref(jmsg); + } + return encoded; +} + +/* TODO: error checking */ +static json_t *trp_encode_route_req(void *req_in) +{ + TALLOC_CTX *tmp_ctx=talloc_new(NULL); + TRP_ROUTE_REQ *req=talloc_get_type(req_in, TRP_ROUTE_REQ); /* null if wrong type */ + TRP_RC rc=TRP_ERROR; + json_t *jbody=NULL; + json_t *jstr=NULL; + char *s=NULL; + + if (req!=NULL) { + jbody=json_object(); + + s=talloc_strndup(tmp_ctx, req->comm->buf, req->comm->len); /* ensures null term */ + if (s==NULL) { + tr_debug("trp_encode_route_req: could not allocate community string"); + json_decref(jbody); + jbody=NULL; + goto cleanup; + } + jstr=json_string(s); + talloc_free(s); + json_object_set_new(jbody, "community", jstr); + + s=talloc_strndup(tmp_ctx, req->realm->buf, req->realm->len); /* ensures null term */ + if (s==NULL) { + tr_debug("trp_encode_route_req: could not allocate realm string"); + json_decref(jbody); + jbody=NULL; + goto cleanup; + } + jstr=json_string(s); + talloc_free(s); + json_object_set_new(jbody, "realm", jstr); + } + +cleanup: + talloc_free(tmp_ctx); + return jbody; +} + +static void trp_route_update_print(void *body_in) { - TRP_MSG_BODY_UPDATE *body=talloc_get_type(body_in, TRP_MSG_BODY_UPDATE); /* null if wrong type */ + TRP_ROUTE_UPDATE *body=talloc_get_type(body_in, TRP_ROUTE_UPDATE); /* null if wrong type */ if (body!=NULL) { printf(" {records=\n"); @@ -486,13 +578,13 @@ static void trp_msg_body_update_print(void *body_in) } } -static void trp_msg_body_route_req_print(void *body_in) +static void trp_route_req_print(void *body_in) { - TRP_MSG_BODY_ROUTE_REQ *body=talloc_get_type(body_in, TRP_MSG_BODY_ROUTE_REQ); /* null if wrong type */ + TRP_ROUTE_REQ *body=talloc_get_type(body_in, TRP_ROUTE_REQ); /* null if wrong type */ if (body!=NULL) { printf(" {community=%.*s\n realm=%.*s}\n", - body->community->len, body->community->buf, + body->comm->len, body->comm->buf, body->realm->len, body->realm->buf); } } @@ -500,7 +592,7 @@ static void trp_msg_body_route_req_print(void *body_in) static void trp_msg_body_print(void *body, TRP_MSG_TYPE msgtype) { struct trp_msg_type_entry *info=get_trp_msg_type_entry(msgtype); - info->printer(body); + info->print(body); } void trp_msg_print(TRP_MSG *msg) @@ -522,7 +614,7 @@ static void *trp_msg_body_new(TALLOC_CTX *mem_ctx, TRP_MSG_TYPE msgtype) return NULL; } - new_body=info->allocator(mem_ctx); + new_body=info->allocate(mem_ctx); msg_body_type_check(msgtype, new_body); /* aborts program on type violation */ return new_body; } @@ -537,7 +629,7 @@ static TRP_RC trp_parse_msg_body(TRP_MSG *msg, json_t *jbody) return TRP_ERROR; } - return info->parser(msg, jbody); + return info->parse(msg, jbody); } -- 2.1.4