diff --git a/include/n2n.h b/include/n2n.h index 5a44b3d..3874609 100644 --- a/include/n2n.h +++ b/include/n2n.h @@ -287,5 +287,5 @@ const char* transop_str (enum n2n_transform tr); void readFromMgmtSocket (n2n_edge_t *eee); -void mgmt_event_post (enum n2n_event_topic topic, void *data); +void mgmt_event_post (enum n2n_event_topic topic, int data0, void *data1); #endif /* _N2N_H_ */ diff --git a/include/n2n_define.h b/include/n2n_define.h index 0226b2b..4c4da21 100644 --- a/include/n2n_define.h +++ b/include/n2n_define.h @@ -124,8 +124,14 @@ enum sn_purge {SN_PURGEABLE = 0, SN_UNPURGEABLE = 1}; enum n2n_event_topic { N2N_EVENT_DEBUG = 0, N2N_EVENT_TEST = 1, + N2N_EVENT_PEER = 2, }; +#define N2N_EVENT_PEER_PURGE 1 +#define N2N_EVENT_PEER_CLEAR 2 +#define N2N_EVENT_PEER_DEL_P2P 3 +#define N2N_EVENT_PEER_ADD_P2P 4 + #define N2N_MGMT_PASSWORD "n2n" /* default password for management port access (so far, json only) */ diff --git a/src/edge_management.c b/src/edge_management.c index 9e562e3..38fb430 100644 --- a/src/edge_management.c +++ b/src/edge_management.c @@ -98,34 +98,63 @@ size_t gen_json_1str (strbuf_t *buf, char *tag, char *_type, char *key, char *va val); } +size_t gen_json_1uint (strbuf_t *buf, char *tag, char *_type, char *key, unsigned int val) { + return snprintf(buf->str, buf->size, + "{" + "\"_tag\":\"%s\"," + "\"_type\":\"%s\"," + "\"%s\":%u}\n", + tag, + _type, + key, + val); +} + static void send_json_1str (mgmt_req_t *req, strbuf_t *buf, char *_type, char *key, char *val) { size_t msg_len = gen_json_1str(buf, req->tag, _type, key, val); send_reply(req, buf, msg_len); } static void send_json_1uint (mgmt_req_t *req, strbuf_t *buf, char *_type, char *key, unsigned int val) { - size_t msg_len = snprintf(buf->str, buf->size, - "{" - "\"_tag\":\"%s\"," - "\"_type\":\"%s\"," - "\"%s\":%u}\n", - req->tag, - _type, - key, - val); + size_t msg_len = gen_json_1uint(buf, req->tag, _type, key, val); send_reply(req, buf, msg_len); } -size_t event_debug (strbuf_t *buf, char *tag, void *data) { +size_t event_debug (strbuf_t *buf, char *tag, int data0, void *data1) { traceEvent(TRACE_DEBUG, "Unexpected call to event_debug"); return 0; } -size_t event_test (strbuf_t *buf, char *tag, void *data) { - size_t msg_len = gen_json_1str(buf, tag, "event", "test", (char *)data); +size_t event_test (strbuf_t *buf, char *tag, int data0, void *data1) { + size_t msg_len = gen_json_1str(buf, tag, "event", "test", (char *)data1); return msg_len; } +size_t event_peer (strbuf_t *buf, char *tag, int data0, void *data1) { + int action = data0; + struct peer_info *peer = (struct peer_info *)data1; + + macstr_t mac_buf; + n2n_sock_str_t sockbuf; + + /* + * Just the peer_info bits that are needed for lookup (maccaddr) or + * firewall and routing (sockaddr) + * If needed, other details can be fetched via the edges method call. + */ + return snprintf(buf->str, buf->size, + "{" + "\"_tag\":\"%s\"," + "\"_type\":\"event\"," + "\"action\":%i," + "\"macaddr\":\"%s\"," + "\"sockaddr\":\"%s\"}\n", + tag, + action, + (is_null_mac(peer->mac_addr)) ? "" : macaddr_str(mac_buf, peer->mac_addr), + sock_to_cstr(sockbuf, &(peer->sock))); +} + static void mgmt_error (mgmt_req_t *req, strbuf_t *buf, char *msg) { send_json_1str(req, buf, "error", "error", msg); } @@ -328,7 +357,7 @@ static void mgmt_packetstats (mgmt_req_t *req, strbuf_t *buf, char *argv0, char static void mgmt_post_test (mgmt_req_t *req, strbuf_t *buf, char *argv0, char *argv) { send_json_1str(req, buf, "row", "sending", "test"); - mgmt_event_post (N2N_EVENT_TEST, argv); + mgmt_event_post (N2N_EVENT_TEST, -1, argv); } static void mgmt_unimplemented (mgmt_req_t *req, strbuf_t *buf, char *argv0, char *argv) { @@ -359,24 +388,29 @@ static const mgmt_handler_t mgmt_handlers[] = { static mgmt_req_t mgmt_event_subscribers[] = { [N2N_EVENT_DEBUG] = { .eee = NULL, .type = N2N_MGMT_UNKNOWN, .tag = "\0" }, [N2N_EVENT_TEST] = { .eee = NULL, .type = N2N_MGMT_UNKNOWN, .tag = "\0" }, + [N2N_EVENT_PEER] = { .eee = NULL, .type = N2N_MGMT_UNKNOWN, .tag = "\0" }, }; /* Map topic number to function */ -static const size_t (*mgmt_events[])(strbuf_t *buf, char *tag, void *data) = { +static const size_t (*mgmt_events[])(strbuf_t *buf, char *tag, int data0, void *data1) = { [N2N_EVENT_DEBUG] = event_debug, [N2N_EVENT_TEST] = event_test, + [N2N_EVENT_PEER] = event_peer, }; /* Allow help and subscriptions to use topic name */ static const mgmt_events_t mgmt_event_names[] = { { .cmd = "debug", .topic = N2N_EVENT_DEBUG, .help = "All events - for event debugging"}, { .cmd = "test", .topic = N2N_EVENT_TEST, .help = "Used only by post.test"}, + { .cmd = "peer", .topic = N2N_EVENT_PEER, .help = "Changes to peer list"}, }; -void mgmt_event_post (enum n2n_event_topic topic, void *data) { +void mgmt_event_post (enum n2n_event_topic topic, int data0, void *data1) { mgmt_req_t *debug = &mgmt_event_subscribers[N2N_EVENT_DEBUG]; mgmt_req_t *sub = &mgmt_event_subscribers[topic]; + traceEvent(TRACE_DEBUG, "post topic=%i data0=%i", topic, data0); + if( sub->type != N2N_MGMT_SUB && debug->type != N2N_MGMT_SUB) { // If neither of this topic or the debug topic have a subscriber // then we dont need to do any work @@ -394,7 +428,7 @@ void mgmt_event_post (enum n2n_event_topic topic, void *data) { tag = debug->tag; } - size_t msg_len = mgmt_events[topic](buf, tag, data); + size_t msg_len = mgmt_events[topic](buf, tag, data0, data1); if (sub->type == N2N_MGMT_SUB) { send_reply(sub, buf, msg_len); diff --git a/src/edge_utils.c b/src/edge_utils.c index 056ef64..fdc47ff 100644 --- a/src/edge_utils.c +++ b/src/edge_utils.c @@ -811,6 +811,7 @@ static void peer_set_p2p_confirmed (n2n_edge_t * eee, scan_tmp = find_peer_by_sock(peer, eee->known_peers); if(scan_tmp != NULL) { HASH_DEL(eee->known_peers, scan_tmp); + mgmt_event_post(N2N_EVENT_PEER,N2N_EVENT_PEER_DEL_P2P,scan); free(scan); scan = scan_tmp; memcpy(scan->mac_addr, mac, sizeof(n2n_mac_t)); @@ -828,6 +829,7 @@ static void peer_set_p2p_confirmed (n2n_edge_t * eee, HASH_ADD_PEER(eee->known_peers, scan); scan->last_p2p = now; + mgmt_event_post(N2N_EVENT_PEER,N2N_EVENT_PEER_ADD_P2P,scan); traceEvent(TRACE_DEBUG, "p2p connection established: %s [%s]", macaddr_str(mac_buf, mac), @@ -994,6 +996,7 @@ static void check_known_peer_sock_change (n2n_edge_t *eee, sock_to_cstr(sockbuf2, peer)); /* The peer has changed public socket. It can no longer be assumed to be reachable. */ HASH_DEL(eee->known_peers, scan); + mgmt_event_post(N2N_EVENT_PEER,N2N_EVENT_PEER_DEL_P2P,scan); free(scan); register_with_new_peer(eee, from_supernode, via_multicast, mac, dev_addr, dev_desc, peer); @@ -1880,6 +1883,7 @@ static int find_peer_destination (n2n_edge_t * eee, * since the peer address may have changed. */ traceEvent(TRACE_DEBUG, "refreshing idle known peer"); HASH_DEL(eee->known_peers, scan); + mgmt_event_post(N2N_EVENT_PEER,N2N_EVENT_PEER_DEL_P2P,scan); free(scan); /* NOTE: registration will be performed upon the receival of the next response packet */ } else { diff --git a/src/n2n.c b/src/n2n.c index a879439..de62e10 100644 --- a/src/n2n.c +++ b/src/n2n.c @@ -636,6 +636,8 @@ size_t purge_peer_list (struct peer_info **peer_list, } } HASH_DEL(*peer_list, scan); + mgmt_event_post(N2N_EVENT_PEER,N2N_EVENT_PEER_PURGE,scan); + /* FIXME: generates events for more than just p2p */ retval++; free(scan); } @@ -652,6 +654,8 @@ size_t clear_peer_list (struct peer_info ** peer_list) { HASH_ITER(hh, *peer_list, scan, tmp) { HASH_DEL(*peer_list, scan); + mgmt_event_post(N2N_EVENT_PEER,N2N_EVENT_PEER_CLEAR,scan); + /* FIXME: generates events for more than just p2p */ retval++; free(scan); }