mirror of
https://github.com/ntop/n2n.git
synced 2024-09-19 16:41:11 +02:00
more sockaddr generalization (#1028)
This commit is contained in:
parent
439dfc6886
commit
95cfbca5a9
|
@ -751,7 +751,11 @@ typedef struct sn_stats {
|
|||
typedef struct node_supernode_association {
|
||||
|
||||
n2n_mac_t mac; /* mac address of an edge */
|
||||
const struct sockaddr_in sock; /* network order socket of that edge's supernode */
|
||||
socklen_t sock_len; /* amount of actually used space (of the following) */
|
||||
union {
|
||||
struct sockaddr sock; /* network order socket of that edge's supernode */
|
||||
struct sockaddr_storage sas; /* the actual memory for it, sockaddr can be too small */
|
||||
};
|
||||
time_t last_seen; /* time mark to keep track of purging requirements */
|
||||
|
||||
UT_hash_handle hh; /* makes this structure hashable */
|
||||
|
@ -796,9 +800,12 @@ struct sn_community_regular_expression {
|
|||
|
||||
|
||||
typedef struct n2n_tcp_connection {
|
||||
int socket_fd; /* file descriptor for tcp socket */
|
||||
struct sockaddr sock; /* network order socket */
|
||||
|
||||
int socket_fd; /* file descriptor for tcp socket */
|
||||
socklen_t sock_len; /* amount of actually used space (of the following) */
|
||||
union {
|
||||
struct sockaddr sock; /* network order socket */
|
||||
struct sockaddr_storage sas; /* memory for it, can be longer than sockaddr */
|
||||
};
|
||||
uint16_t expected; /* number of bytes expected to be read */
|
||||
uint16_t position; /* current position in the buffer */
|
||||
uint8_t buffer[N2N_PKT_BUF_SIZE + sizeof(uint16_t)]; /* buffer for data collected from tcp socket incl. prepended length */
|
||||
|
|
|
@ -417,7 +417,6 @@ void readFromMgmtSocket (n2n_edge_t *eee) {
|
|||
ssize_t recvlen;
|
||||
/* ssize_t sendlen; */
|
||||
mgmt_req_t req;
|
||||
socklen_t i;
|
||||
size_t msg_len;
|
||||
time_t now;
|
||||
struct peer_info *peer, *tmpPeer;
|
||||
|
@ -438,11 +437,11 @@ void readFromMgmtSocket (n2n_edge_t *eee) {
|
|||
req.mgmt_sock = eee->udp_mgmt_sock;
|
||||
req.keep_running = eee->keep_running;
|
||||
req.mgmt_password_hash = eee->conf.mgmt_password_hash;
|
||||
req.sock_len = sizeof(req.sas);
|
||||
|
||||
now = time(NULL);
|
||||
i = sizeof(req.sender_sock);
|
||||
recvlen = recvfrom(eee->udp_mgmt_sock, udp_buf, N2N_PKT_BUF_SIZE, 0 /*flags*/,
|
||||
(struct sockaddr *) &req.sender_sock, (socklen_t *) &i);
|
||||
&req.sender_sock, &req.sock_len);
|
||||
|
||||
if(recvlen < 0) {
|
||||
traceEvent(TRACE_WARNING, "mgmt recvfrom failed: %d - %s", errno, strerror(errno));
|
||||
|
@ -546,7 +545,7 @@ void readFromMgmtSocket (n2n_edge_t *eee) {
|
|||
(peer->last_seen) ? time_buf : "");
|
||||
|
||||
sendto(eee->udp_mgmt_sock, udp_buf, msg_len, 0,
|
||||
(struct sockaddr *) &req.sender_sock, sizeof(struct sockaddr_in));
|
||||
&req.sender_sock, req.sock_len);
|
||||
msg_len = 0;
|
||||
}
|
||||
|
||||
|
@ -570,7 +569,7 @@ void readFromMgmtSocket (n2n_edge_t *eee) {
|
|||
(peer->last_seen) ? time_buf : "");
|
||||
|
||||
sendto(eee->udp_mgmt_sock, udp_buf, msg_len, 0,
|
||||
(struct sockaddr *) &req.sender_sock, sizeof(struct sockaddr_in));
|
||||
&req.sender_sock, req.sock_len);
|
||||
msg_len = 0;
|
||||
}
|
||||
|
||||
|
@ -596,7 +595,7 @@ void readFromMgmtSocket (n2n_edge_t *eee) {
|
|||
(peer->uptime) ? uptime_buf : "");
|
||||
|
||||
sendto(eee->udp_mgmt_sock, udp_buf, msg_len, 0,
|
||||
(struct sockaddr *) &req.sender_sock, sizeof(struct sockaddr_in));
|
||||
&req.sender_sock, req.sock_len);
|
||||
msg_len = 0;
|
||||
}
|
||||
|
||||
|
@ -643,5 +642,5 @@ void readFromMgmtSocket (n2n_edge_t *eee) {
|
|||
"\nType \"help\" to see more commands.\n\n");
|
||||
|
||||
sendto(eee->udp_mgmt_sock, udp_buf, msg_len, 0,
|
||||
(struct sockaddr *) &req.sender_sock, sizeof(struct sockaddr_in));
|
||||
&req.sender_sock, req.sock_len);
|
||||
}
|
||||
|
|
|
@ -21,7 +21,7 @@ int getTraceLevel ();
|
|||
ssize_t send_reply (mgmt_req_t *req, strbuf_t *buf, size_t msg_len) {
|
||||
// TODO: better error handling (counters?)
|
||||
return sendto(req->mgmt_sock, buf->str, msg_len, 0,
|
||||
(struct sockaddr *) &req->sender_sock, sizeof(struct sockaddr_in));
|
||||
&req->sender_sock, req->sock_len);
|
||||
}
|
||||
|
||||
size_t gen_json_1str (strbuf_t *buf, char *tag, char *_type, char *key, char *val) {
|
||||
|
|
|
@ -39,7 +39,11 @@ typedef struct mgmt_req {
|
|||
char *argv0;
|
||||
char *argv;
|
||||
char tag[10];
|
||||
struct sockaddr_in sender_sock;
|
||||
socklen_t sock_len;
|
||||
union {
|
||||
struct sockaddr sender_sock;
|
||||
struct sockaddr_storage sas; // memory for the socket, actual socket can be longer than sockaddr
|
||||
};
|
||||
} mgmt_req_t;
|
||||
|
||||
/*
|
||||
|
|
|
@ -255,12 +255,12 @@ static void handleMgmtJson (mgmt_req_t *req, char *udp_buf, const int recvlen) {
|
|||
}
|
||||
|
||||
static int sendto_mgmt (n2n_sn_t *sss,
|
||||
const struct sockaddr_in *sender_sock,
|
||||
const struct sockaddr *sender_sock, socklen_t sock_size,
|
||||
const uint8_t *mgmt_buf,
|
||||
size_t mgmt_size) {
|
||||
|
||||
ssize_t r = sendto(sss->mgmt_sock, (void *)mgmt_buf, mgmt_size, 0 /*flags*/,
|
||||
(struct sockaddr *)sender_sock, sizeof (struct sockaddr_in));
|
||||
sender_sock, sock_size);
|
||||
|
||||
if(r <= 0) {
|
||||
++(sss->stats.errors);
|
||||
|
@ -272,7 +272,7 @@ static int sendto_mgmt (n2n_sn_t *sss,
|
|||
}
|
||||
|
||||
int process_mgmt (n2n_sn_t *sss,
|
||||
const struct sockaddr_in *sender_sock,
|
||||
const struct sockaddr *sender_sock, socklen_t sock_size,
|
||||
char *mgmt_buf,
|
||||
size_t mgmt_size,
|
||||
time_t now) {
|
||||
|
@ -297,7 +297,8 @@ int process_mgmt (n2n_sn_t *sss,
|
|||
req.mgmt_sock = sss->mgmt_sock;
|
||||
req.keep_running = sss->keep_running;
|
||||
req.mgmt_password_hash = sss->mgmt_password_hash;
|
||||
memcpy(&req.sender_sock, sender_sock, sizeof(req.sender_sock));
|
||||
memcpy(&req.sender_sock, sender_sock, sock_size);
|
||||
req.sock_len = sock_size;
|
||||
|
||||
/* avoid parsing any uninitialized junk from the stack */
|
||||
mgmt_buf[mgmt_size] = 0;
|
||||
|
@ -309,7 +310,7 @@ int process_mgmt (n2n_sn_t *sss,
|
|||
"\thelp | This help message\n"
|
||||
"\treload_communities | Reloads communities and user's public keys\n"
|
||||
"\t<enter> | Display status and statistics\n");
|
||||
sendto_mgmt(sss, sender_sock, (const uint8_t *) resbuf, ressize);
|
||||
sendto_mgmt(sss, sender_sock, sock_size, (const uint8_t *) resbuf, ressize);
|
||||
return 0; /* no status output afterwards */
|
||||
}
|
||||
|
||||
|
@ -317,7 +318,7 @@ int process_mgmt (n2n_sn_t *sss,
|
|||
if(!sss->community_file) {
|
||||
ressize += snprintf(resbuf + ressize, N2N_SN_PKTBUF_SIZE - ressize,
|
||||
"No community file provided (-c command line option)\n");
|
||||
sendto_mgmt(sss, sender_sock, (const uint8_t *) resbuf, ressize);
|
||||
sendto_mgmt(sss, sender_sock, sock_size, (const uint8_t *) resbuf, ressize);
|
||||
return 0; /* no status output afterwards */
|
||||
}
|
||||
traceEvent(TRACE_NORMAL, "'reload_communities' command");
|
||||
|
@ -325,12 +326,12 @@ int process_mgmt (n2n_sn_t *sss,
|
|||
if(load_allowed_sn_community(sss)) {
|
||||
ressize += snprintf(resbuf + ressize, N2N_SN_PKTBUF_SIZE - ressize,
|
||||
"Error while re-loading community file (not found or no valid content)\n");
|
||||
sendto_mgmt(sss, sender_sock, (const uint8_t *) resbuf, ressize);
|
||||
sendto_mgmt(sss, sender_sock, sock_size, (const uint8_t *) resbuf, ressize);
|
||||
return 0; /* no status output afterwards */
|
||||
}
|
||||
ressize += snprintf(resbuf + ressize, N2N_SN_PKTBUF_SIZE - ressize,
|
||||
"OK.\n");
|
||||
sendto_mgmt(sss, sender_sock, (const uint8_t *) resbuf, ressize);
|
||||
sendto_mgmt(sss, sender_sock, sock_size, (const uint8_t *) resbuf, ressize);
|
||||
return 0; /* no status output afterwards */
|
||||
}
|
||||
|
||||
|
@ -357,7 +358,7 @@ int process_mgmt (n2n_sn_t *sss,
|
|||
"%s '%s'\n",
|
||||
(community->is_federation) ? "FEDERATION" : ((community->purgeable == UNPURGEABLE) ? "FIXED NAME COMMUNITY" : "COMMUNITY"),
|
||||
(community->is_federation) ? "-/-" : community->community);
|
||||
sendto_mgmt(sss, sender_sock, (const uint8_t *) resbuf, ressize);
|
||||
sendto_mgmt(sss, sender_sock, sock_size, (const uint8_t *) resbuf, ressize);
|
||||
ressize = 0;
|
||||
|
||||
num = 0;
|
||||
|
@ -373,7 +374,7 @@ int process_mgmt (n2n_sn_t *sss,
|
|||
peer->dev_desc,
|
||||
(peer->last_seen) ? time_buf : "");
|
||||
|
||||
sendto_mgmt(sss, sender_sock, (const uint8_t *) resbuf, ressize);
|
||||
sendto_mgmt(sss, sender_sock, sock_size, (const uint8_t *) resbuf, ressize);
|
||||
ressize = 0;
|
||||
}
|
||||
}
|
||||
|
@ -418,7 +419,7 @@ int process_mgmt (n2n_sn_t *sss,
|
|||
"last reg %lu sec ago\n\n",
|
||||
(long unsigned int) (now - sss->stats.last_reg_super));
|
||||
|
||||
sendto_mgmt(sss, sender_sock, (const uint8_t *) resbuf, ressize);
|
||||
sendto_mgmt(sss, sender_sock, sock_size, (const uint8_t *) resbuf, ressize);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
127
src/sn_utils.c
127
src/sn_utils.c
|
@ -57,13 +57,13 @@ static int sort_communities (n2n_sn_t *sss,
|
|||
time_t now);
|
||||
|
||||
int process_mgmt (n2n_sn_t *sss,
|
||||
const struct sockaddr_in *sender_sock,
|
||||
char *mgmt_buf,
|
||||
size_t mgmt_size,
|
||||
time_t now);
|
||||
const struct sockaddr *sender_sock, socklen_t sock_size,
|
||||
char *mgmt_buf,
|
||||
size_t mgmt_size,
|
||||
time_t now);
|
||||
|
||||
static int process_udp (n2n_sn_t *sss,
|
||||
const struct sockaddr_in *sender_sock,
|
||||
const struct sockaddr *sender_sock, socklen_t sock_size,
|
||||
const SOCKET socket_fd,
|
||||
uint8_t *udp_buf,
|
||||
size_t udp_size,
|
||||
|
@ -700,7 +700,7 @@ static int try_forward (n2n_sn_t * sss,
|
|||
if(assoc) {
|
||||
traceEvent(TRACE_DEBUG, "found mac address associated with a known supernode, forwarding packet to that supernode");
|
||||
sendto_sock(sss, sss->sock,
|
||||
(const struct sockaddr*)&(assoc->sock),
|
||||
&(assoc->sock),
|
||||
pktbuf, pktsize);
|
||||
} else {
|
||||
// forwarding packet to all federated supernodes
|
||||
|
@ -876,7 +876,7 @@ void sn_term (n2n_sn_t *sss) {
|
|||
}
|
||||
|
||||
void update_node_supernode_association (struct sn_community *comm,
|
||||
n2n_mac_t *edgeMac, const struct sockaddr_in *sender_sock,
|
||||
n2n_mac_t *edgeMac, const struct sockaddr *sender_sock, socklen_t sock_size,
|
||||
time_t now) {
|
||||
|
||||
node_supernode_association_t *assoc;
|
||||
|
@ -884,15 +884,17 @@ void update_node_supernode_association (struct sn_community *comm,
|
|||
HASH_FIND(hh, comm->assoc, edgeMac, sizeof(n2n_mac_t), assoc);
|
||||
if(!assoc) {
|
||||
// create a new association
|
||||
assoc = (node_supernode_association_t*)malloc(sizeof(node_supernode_association_t));
|
||||
assoc = (node_supernode_association_t*)calloc(1, sizeof(node_supernode_association_t));
|
||||
if(assoc) {
|
||||
memcpy(&(assoc->mac), edgeMac, sizeof(n2n_mac_t));
|
||||
memcpy((struct sockaddr_in*)&(assoc->sock), sender_sock, sizeof(struct sockaddr_in));
|
||||
memcpy(&(assoc->sock), sender_sock, sock_size);
|
||||
assoc->sock_len = sock_size;
|
||||
assoc->last_seen = now;
|
||||
HASH_ADD(hh, comm->assoc, mac, sizeof(n2n_mac_t), assoc);
|
||||
} else {
|
||||
// already there, update socket and time only
|
||||
memcpy((struct sockaddr_in*)&(assoc->sock), sender_sock, sizeof(struct sockaddr_in));
|
||||
memcpy(&(assoc->sock), sender_sock, sock_size);
|
||||
assoc->sock_len = sock_size;
|
||||
assoc->last_seen = now;
|
||||
}
|
||||
}
|
||||
|
@ -1509,7 +1511,7 @@ static int sort_communities (n2n_sn_t *sss,
|
|||
*
|
||||
*/
|
||||
static int process_udp (n2n_sn_t * sss,
|
||||
const struct sockaddr_in *sender_sock,
|
||||
const struct sockaddr *sender_sock, socklen_t sock_size,
|
||||
const SOCKET socket_fd,
|
||||
uint8_t * udp_buf,
|
||||
size_t udp_size,
|
||||
|
@ -1522,10 +1524,10 @@ static int process_udp (n2n_sn_t * sss,
|
|||
uint8_t from_supernode;
|
||||
peer_info_t *sn = NULL;
|
||||
n2n_sock_t sender;
|
||||
n2n_sock_t *orig_sender;
|
||||
macstr_t mac_buf;
|
||||
macstr_t mac_buf2;
|
||||
n2n_sock_str_t sockbuf;
|
||||
char buf[32];
|
||||
uint8_t hash_buf[16] = {0}; /* always size of 16 (max) despite the actual value of N2N_REG_SUP_HASH_CHECK_LEN (<= 16) */
|
||||
|
||||
struct sn_community *comm, *tmp;
|
||||
|
@ -1534,9 +1536,12 @@ static int process_udp (n2n_sn_t * sss,
|
|||
int skip_add;
|
||||
time_t any_time = 0;
|
||||
|
||||
traceEvent(TRACE_DEBUG, "processing incoming UDP packet [len: %lu][sender: %s:%u]",
|
||||
udp_size, intoa(ntohl(sender_sock->sin_addr.s_addr), buf, sizeof(buf)),
|
||||
ntohs(sender_sock->sin_port));
|
||||
memset(&sender, 0, sizeof(n2n_sock_t));
|
||||
fill_n2nsock(&sender, sender_sock);
|
||||
orig_sender = &sender;
|
||||
|
||||
traceEvent(TRACE_DEBUG, "processing incoming UDP packet [len: %lu][sender: %s]",
|
||||
udp_size, sock_to_cstr(sockbuf, &sender));
|
||||
|
||||
/* check if header is unencrypted. the following check is around 99.99962 percent reliable.
|
||||
* it heavily relies on the structure of packet's common part
|
||||
|
@ -1652,11 +1657,6 @@ static int process_udp (n2n_sn_t * sss,
|
|||
}
|
||||
}
|
||||
|
||||
/* REVISIT: when UDP/IPv6 is supported we will need a flag to indicate which
|
||||
* IP transport version the packet arrived on. May need to UDP sockets. */
|
||||
memset(&sender, 0, sizeof(n2n_sock_t));
|
||||
fill_n2nsock(&sender, (struct sockaddr*)sender_sock);
|
||||
|
||||
from_supernode = cmn.flags & N2N_FLAGS_FROM_SUPERNODE;
|
||||
if(from_supernode) {
|
||||
skip_add = SN_ADD_SKIP;
|
||||
|
@ -1718,7 +1718,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
/* We are going to add socket even if it was not there before */
|
||||
cmn2.flags |= N2N_FLAGS_SOCKET | N2N_FLAGS_FROM_SUPERNODE;
|
||||
|
||||
fill_n2nsock(&pkt.sock, (struct sockaddr*)sender_sock);
|
||||
memcpy(&pkt.sock, &sender, sizeof(sender));
|
||||
|
||||
rec_buf = encbuf;
|
||||
/* Re-encode the header. */
|
||||
|
@ -1801,7 +1801,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
/* We are going to add socket even if it was not there before */
|
||||
cmn2.flags |= N2N_FLAGS_SOCKET | N2N_FLAGS_FROM_SUPERNODE;
|
||||
|
||||
fill_n2nsock(®.sock, (struct sockaddr*)sender_sock);
|
||||
memcpy(®.sock, &sender, sizeof(sender));
|
||||
|
||||
/* Re-encode the header. */
|
||||
encode_REGISTER(encbuf, &encx, &cmn2, ®);
|
||||
|
@ -1960,7 +1960,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
|
||||
ack.lifetime = reg_lifetime(sss);
|
||||
|
||||
fill_n2nsock(&ack.sock, (struct sockaddr*)sender_sock);
|
||||
memcpy(&ack.sock, &sender, sizeof(sender));
|
||||
|
||||
/* Add sender's data to federation (or update it) */
|
||||
if(comm->is_federation == IS_FEDERATION) {
|
||||
|
@ -2029,7 +2029,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
encode_buf(ackbuf, &encx, hash_buf /* no matter what content */, N2N_REG_SUP_HASH_CHECK_LEN);
|
||||
}
|
||||
}
|
||||
sendto_sock(sss, socket_fd, (struct sockaddr *)sender_sock, ackbuf, encx);
|
||||
sendto_sock(sss, socket_fd, sender_sock, ackbuf, encx);
|
||||
|
||||
traceEvent(TRACE_DEBUG, "Tx REGISTER_SUPER_NAK for %s",
|
||||
macaddr_str(mac_buf, reg.edgeMac));
|
||||
|
@ -2041,7 +2041,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
// NULL comm and from_supernode parameter)
|
||||
// exception: do not forward auto ip draw
|
||||
if(!is_null_mac(reg.edgeMac)) {
|
||||
fill_n2nsock(®.sock, (struct sockaddr*)sender_sock);
|
||||
memcpy(®.sock, &sender, sizeof(sender));
|
||||
|
||||
cmn2.pc = n2n_register_super;
|
||||
encode_REGISTER_SUPER(ackbuf, &encx, &cmn2, ®);
|
||||
|
@ -2100,7 +2100,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
}
|
||||
}
|
||||
|
||||
sendto_sock(sss, socket_fd, (struct sockaddr *)sender_sock, ackbuf, encx);
|
||||
sendto_sock(sss, socket_fd, sender_sock, ackbuf, encx);
|
||||
|
||||
traceEvent(TRACE_DEBUG, "Tx REGISTER_SUPER_ACK for %s [%s]",
|
||||
macaddr_str(mac_buf, reg.edgeMac),
|
||||
|
@ -2108,7 +2108,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
} else {
|
||||
// this is an edge with valid authentication registering with another supernode, so ...
|
||||
// 1- ... associate it with that other supernode
|
||||
update_node_supernode_association(comm, &(reg.edgeMac), sender_sock, now);
|
||||
update_node_supernode_association(comm, &(reg.edgeMac), sender_sock, sock_size, now);
|
||||
// 2- ... we can delete it from regular list if present (can happen)
|
||||
HASH_FIND_PEER(comm->edges, reg.edgeMac, peer);
|
||||
if(peer != NULL) {
|
||||
|
@ -2179,17 +2179,10 @@ static int process_udp (n2n_sn_t * sss,
|
|||
n2n_sock_str_t sockbuf1;
|
||||
n2n_sock_str_t sockbuf2;
|
||||
macstr_t mac_buf1;
|
||||
n2n_sock_t sender;
|
||||
n2n_sock_t *orig_sender;
|
||||
int i;
|
||||
uint8_t dec_tmpbuf[REG_SUPER_ACK_PAYLOAD_SPACE];
|
||||
n2n_REGISTER_SUPER_ACK_payload_t *payload;
|
||||
|
||||
memset(&sender, 0, sizeof(n2n_sock_t));
|
||||
fill_n2nsock(&sender, (struct sockaddr*)sender_sock);
|
||||
|
||||
orig_sender = &sender;
|
||||
|
||||
memset(&ack, 0, sizeof(n2n_REGISTER_SUPER_ACK_t));
|
||||
|
||||
if(!comm) {
|
||||
|
@ -2268,10 +2261,6 @@ static int process_udp (n2n_sn_t * sss,
|
|||
struct peer_info *peer;
|
||||
n2n_sock_str_t sockbuf;
|
||||
macstr_t mac_buf;
|
||||
n2n_sock_t sender;
|
||||
|
||||
memset(&sender, 0, sizeof(n2n_sock_t));
|
||||
fill_n2nsock(&sender, (struct sockaddr*)sender_sock);
|
||||
|
||||
memset(&nak, 0, sizeof(n2n_REGISTER_SUPER_NAK_t));
|
||||
|
||||
|
@ -2389,7 +2378,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
memcpy(pi.mac, query.targetMac, sizeof(n2n_mac_t));
|
||||
memcpy(pi.srcMac, sss->mac_addr, sizeof(n2n_mac_t));
|
||||
|
||||
fill_n2nsock(&pi.sock, (struct sockaddr*)sender_sock);
|
||||
memcpy(&pi.sock, &sender, sizeof(sender));
|
||||
|
||||
pi.load = sn_selection_criterion_gather_data(sss);
|
||||
|
||||
|
@ -2406,7 +2395,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
}
|
||||
}
|
||||
|
||||
sendto_sock(sss, socket_fd, (struct sockaddr *)sender_sock, encbuf, encx);
|
||||
sendto_sock(sss, socket_fd, sender_sock, encbuf, encx);
|
||||
|
||||
traceEvent(TRACE_DEBUG, "Tx PONG to %s",
|
||||
macaddr_str(mac_buf, query.srcMac));
|
||||
|
@ -2448,7 +2437,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
time_stamp());
|
||||
}
|
||||
// back to sender, be it edge or supernode (which will forward to edge)
|
||||
sendto_sock(sss, socket_fd, (struct sockaddr *)sender_sock, encbuf, encx);
|
||||
sendto_sock(sss, socket_fd, sender_sock, encbuf, encx);
|
||||
|
||||
traceEvent(TRACE_DEBUG, "Tx PEER_INFO to %s",
|
||||
macaddr_str(mac_buf, query.srcMac));
|
||||
|
@ -2508,7 +2497,7 @@ static int process_udp (n2n_sn_t * sss,
|
|||
if(peer != NULL) {
|
||||
if((comm->is_federation == IS_NO_FEDERATION) && (!is_null_mac(pi.srcMac))) {
|
||||
// snoop on the information to use for supernode forwarding (do not wait until first remote REGISTER_SUPER)
|
||||
update_node_supernode_association(comm, &(pi.mac), sender_sock, now);
|
||||
update_node_supernode_association(comm, &(pi.mac), sender_sock, sock_size, now);
|
||||
|
||||
// this is a PEER_INFO for one of the edges conencted to this supernode, forward,
|
||||
// i.e. re-assemble (memcpy of udpbuf to encbuf could be sufficient as well)
|
||||
|
@ -2597,12 +2586,12 @@ int run_sn_loop (n2n_sn_t *sss) {
|
|||
|
||||
// external udp
|
||||
if(FD_ISSET(sss->sock, &socket_mask)) {
|
||||
struct sockaddr_in sender_sock;
|
||||
socklen_t i;
|
||||
struct sockaddr_storage sas;
|
||||
struct sockaddr *sender_sock = (struct sockaddr*)&sas;
|
||||
socklen_t ss_size = sizeof(sas);
|
||||
|
||||
i = sizeof(sender_sock);
|
||||
bread = recvfrom(sss->sock, (void *)pktbuf, N2N_SN_PKTBUF_SIZE, 0 /*flags*/,
|
||||
(struct sockaddr *)&sender_sock, (socklen_t *)&i);
|
||||
sender_sock, &ss_size);
|
||||
|
||||
if((bread < 0)
|
||||
#ifdef WIN32
|
||||
|
@ -2622,7 +2611,7 @@ int run_sn_loop (n2n_sn_t *sss) {
|
|||
// we have a datagram to process...
|
||||
if(bread > 0) {
|
||||
// ...and the datagram has data (not just a header)
|
||||
process_udp(sss, &sender_sock, sss->sock, pktbuf, bread, now);
|
||||
process_udp(sss, sender_sock, ss_size, sss->sock, pktbuf, bread, now);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2640,17 +2629,16 @@ int run_sn_loop (n2n_sn_t *sss) {
|
|||
continue;
|
||||
|
||||
if(FD_ISSET(conn->socket_fd, &socket_mask)) {
|
||||
struct sockaddr_storage sas;
|
||||
struct sockaddr *sender_sock = (struct sockaddr*)&sas;
|
||||
socklen_t ss_size = sizeof(sas);
|
||||
|
||||
struct sockaddr_in sender_sock;
|
||||
socklen_t i;
|
||||
|
||||
i = sizeof(sender_sock);
|
||||
bread = recvfrom(conn->socket_fd,
|
||||
conn->buffer + conn->position, conn->expected - conn->position, 0 /*flags*/,
|
||||
(struct sockaddr *)&sender_sock, (socklen_t *)&i);
|
||||
sender_sock, &ss_size);
|
||||
|
||||
if(bread <= 0) {
|
||||
traceEvent(TRACE_INFO, "closing tcp connection to [%s]", sock_to_cstr(sockbuf, (n2n_sock_t*)&sender_sock));
|
||||
traceEvent(TRACE_INFO, "closing tcp connection to [%s]", sock_to_cstr(sockbuf, (n2n_sock_t*)sender_sock));
|
||||
traceEvent(TRACE_DEBUG, "recvfrom() returns %d and sees errno %d (%s)", bread, errno, strerror(errno));
|
||||
#ifdef WIN32
|
||||
traceEvent(TRACE_DEBUG, "WSAGetLastError(): %u", WSAGetLastError());
|
||||
|
@ -2665,14 +2653,14 @@ int run_sn_loop (n2n_sn_t *sss) {
|
|||
// the prepended length has been read, preparing for the packet
|
||||
conn->expected += be16toh(*(uint16_t*)(conn->buffer));
|
||||
if(conn->expected > N2N_SN_PKTBUF_SIZE) {
|
||||
traceEvent(TRACE_INFO, "closing tcp connection to [%s]", sock_to_cstr(sockbuf, (n2n_sock_t*)&sender_sock));
|
||||
traceEvent(TRACE_INFO, "closing tcp connection to [%s]", sock_to_cstr(sockbuf, (n2n_sock_t*)sender_sock));
|
||||
traceEvent(TRACE_DEBUG, "too many bytes in tcp packet expected");
|
||||
close_tcp_connection(sss, conn);
|
||||
continue;
|
||||
}
|
||||
} else {
|
||||
// full packet read, handle it
|
||||
process_udp(sss, (struct sockaddr_in*)&(conn->sock), conn->socket_fd,
|
||||
process_udp(sss, &(conn->sock), conn->sock_len, conn->socket_fd,
|
||||
conn->buffer + sizeof(uint16_t), conn->position - sizeof(uint16_t), now);
|
||||
|
||||
// reset, await new prepended length
|
||||
|
@ -2693,42 +2681,45 @@ int run_sn_loop (n2n_sn_t *sss) {
|
|||
|
||||
// accept new incoming tcp connection
|
||||
if(FD_ISSET(sss->tcp_sock, &socket_mask)) {
|
||||
struct sockaddr_in sender_sock;
|
||||
socklen_t i;
|
||||
struct sockaddr_storage sas;
|
||||
struct sockaddr *sender_sock = (struct sockaddr*)&sas;
|
||||
socklen_t ss_size = sizeof(sas);
|
||||
|
||||
i = sizeof(sender_sock);
|
||||
if((HASH_COUNT(sss->tcp_connections) + 4) < FD_SETSIZE) {
|
||||
tmp_sock = accept(sss->tcp_sock, (struct sockaddr *)&sender_sock, (socklen_t *)&i);
|
||||
tmp_sock = accept(sss->tcp_sock, sender_sock, &ss_size);
|
||||
// REVISIT: should we error out if ss_size returns bigger than before? can this ever happen?
|
||||
if(tmp_sock >= 0) {
|
||||
conn = (n2n_tcp_connection_t*)malloc(sizeof(n2n_tcp_connection_t));
|
||||
conn = (n2n_tcp_connection_t*)calloc(1, sizeof(n2n_tcp_connection_t));
|
||||
if(conn) {
|
||||
conn->socket_fd = tmp_sock;
|
||||
memcpy(&(conn->sock), &sender_sock, sizeof(struct sockaddr_in));
|
||||
memcpy(&(conn->sock), sender_sock, ss_size);
|
||||
conn->sock_len = ss_size;
|
||||
conn->inactive = 0;
|
||||
conn->expected = sizeof(uint16_t);
|
||||
conn->position = 0;
|
||||
HASH_ADD_INT(sss->tcp_connections, socket_fd, conn);
|
||||
traceEvent(TRACE_INFO, "accepted incoming TCP connection from [%s]",
|
||||
sock_to_cstr(sockbuf, (n2n_sock_t*)&sender_sock));
|
||||
sock_to_cstr(sockbuf, (n2n_sock_t*)sender_sock));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// no space to store the socket for a new connection, close immediately
|
||||
traceEvent(TRACE_DEBUG, "denied incoming TCP connection from [%s] due to max connections limit hit",
|
||||
sock_to_cstr(sockbuf, (n2n_sock_t*)&sender_sock));
|
||||
sock_to_cstr(sockbuf, (n2n_sock_t*)sender_sock));
|
||||
}
|
||||
}
|
||||
#endif /* N2N_HAVE_TCP */
|
||||
|
||||
// handle management port input
|
||||
if(FD_ISSET(sss->mgmt_sock, &socket_mask)) {
|
||||
struct sockaddr_in sender_sock;
|
||||
size_t i;
|
||||
struct sockaddr_storage sas;
|
||||
struct sockaddr *sender_sock = (struct sockaddr*)&sas;
|
||||
socklen_t ss_size = sizeof(sas);
|
||||
|
||||
i = sizeof(sender_sock);
|
||||
bread = recvfrom(sss->mgmt_sock, (void *)pktbuf, N2N_SN_PKTBUF_SIZE, 0 /*flags*/,
|
||||
(struct sockaddr *)&sender_sock, (socklen_t *)&i);
|
||||
sender_sock, &ss_size);
|
||||
|
||||
// REVISIT: should we error out if ss_size returns bigger than before? can this ever happen?
|
||||
if(bread <= 0) {
|
||||
traceEvent(TRACE_ERROR, "recvfrom() failed %d errno %d (%s)", bread, errno, strerror(errno));
|
||||
*sss->keep_running = 0;
|
||||
|
@ -2736,7 +2727,7 @@ int run_sn_loop (n2n_sn_t *sss) {
|
|||
}
|
||||
|
||||
// we have a datagram to process
|
||||
process_mgmt(sss, &sender_sock, (char *)pktbuf, bread, now);
|
||||
process_mgmt(sss, sender_sock, ss_size, (char *)pktbuf, bread, now);
|
||||
}
|
||||
|
||||
} else {
|
||||
|
|
Loading…
Reference in New Issue
Block a user