X-Git-Url: https://git.octo.it/?a=blobdiff_plain;f=src%2Ftcpconns.c;h=0236c9d0fc6dbbf6ede8da7fcfa90709e65f3ac9;hb=9817e7298bd6c364fa17347327af54adf048bd21;hp=6351c7b68853390905b35b327a101d4af58ee960;hpb=37a82b6340ad2748e667a96b5af5c617edb3c72d;p=collectd.git diff --git a/src/tcpconns.c b/src/tcpconns.c index 6351c7b6..0236c9d0 100644 --- a/src/tcpconns.c +++ b/src/tcpconns.c @@ -17,7 +17,7 @@ * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * * Author: - * Florian octo Forster + * Florian octo Forster * Michael Stapelberg **/ @@ -219,13 +219,13 @@ static const char *tcp_state[] = "CLOSED", "LISTEN", "SYN_SENT", - "SYN_RCVD", + "SYN_RECV", "ESTABLISHED", "CLOSE_WAIT", - "FIN_WAIT_1", + "FIN_WAIT1", "CLOSING", "LAST_ACK", - "FIN_WAIT_2", + "FIN_WAIT2", "TIME_WAIT" }; @@ -272,12 +272,15 @@ static const char *config_keys[] = { "ListeningPorts", "LocalPort", - "RemotePort" + "RemotePort", + "AllPortsSummary" }; static int config_keys_num = STATIC_ARRAY_SIZE (config_keys); static int port_collect_listening = 0; +static int port_collect_total = 0; static port_entry_t *port_list_head = NULL; +static uint32_t count_total[TCP_STATE_MAX + 1]; #if KERNEL_LINUX #if HAVE_STRUCT_LINUX_INET_DIAG_REQ @@ -295,17 +298,22 @@ enum } linux_source = SRC_DUNNO; #endif +static void conn_prepare_vl (value_list_t *vl, value_t *values) +{ + vl->values = values; + vl->values_len = 1; + sstrncpy (vl->host, hostname_g, sizeof (vl->host)); + sstrncpy (vl->plugin, "tcpconns", sizeof (vl->plugin)); + sstrncpy (vl->type, "tcp_connections", sizeof (vl->type)); +} + static void conn_submit_port_entry (port_entry_t *pe) { value_t values[1]; value_list_t vl = VALUE_LIST_INIT; int i; - vl.values = values; - vl.values_len = 1; - sstrncpy (vl.host, hostname_g, sizeof (vl.host)); - sstrncpy (vl.plugin, "tcpconns", sizeof (vl.plugin)); - sstrncpy (vl.type, "tcp_connections", sizeof (vl.type)); + conn_prepare_vl (&vl, values); if (((port_collect_listening != 0) && (pe->flags & PORT_IS_LISTENING)) || (pe->flags & PORT_COLLECT_LOCAL)) @@ -339,10 +347,33 @@ static void conn_submit_port_entry (port_entry_t *pe) } } /* void conn_submit */ +static void conn_submit_port_total (void) +{ + value_t values[1]; + value_list_t vl = VALUE_LIST_INIT; + int i; + + conn_prepare_vl (&vl, values); + + sstrncpy (vl.plugin_instance, "all", sizeof (vl.plugin_instance)); + + for (i = 1; i <= TCP_STATE_MAX; i++) + { + vl.values[0].gauge = count_total[i]; + + sstrncpy (vl.type_instance, tcp_state[i], sizeof (vl.type_instance)); + + plugin_dispatch_values (&vl); + } +} + static void conn_submit_all (void) { port_entry_t *pe; + if (port_collect_total) + conn_submit_port_total (); + for (pe = port_list_head; pe != NULL; pe = pe->next) conn_submit_port_entry (pe); } /* void conn_submit_all */ @@ -381,6 +412,8 @@ static void conn_reset_port_entry (void) port_entry_t *prev = NULL; port_entry_t *pe = port_list_head; + memset (&count_total, '\0', sizeof(count_total)); + while (pe != NULL) { /* If this entry was created while reading the files (ant not when handling @@ -428,6 +461,8 @@ static int conn_handle_ports (uint16_t port_local, uint16_t port_remote, uint8_t return (-1); } + count_total[state]++; + /* Listening sockets */ if ((state == TCP_STATE_LISTEN) && (port_collect_listening != 0)) { @@ -704,6 +739,13 @@ static int conn_config (const char *key, const char *value) else pe->flags |= PORT_COLLECT_REMOTE; } + else if (strcasecmp (key, "AllPortsSummary") == 0) + { + if (IS_TRUE (value)) + port_collect_total = 1; + else + port_collect_total = 0; + } else { return (-1); @@ -715,7 +757,7 @@ static int conn_config (const char *key, const char *value) #if KERNEL_LINUX static int conn_init (void) { - if (port_list_head == NULL) + if (port_collect_total == 0 && port_list_head == NULL) port_collect_listening = 1; return (0); @@ -909,7 +951,9 @@ static int conn_init (void) static int conn_read (void) { struct inpcbtable table; +#if !defined(__OpenBSD__) && (defined(__NetBSD_Version__) && __NetBSD_Version__ <= 699002700) struct inpcb *head; +#endif struct inpcb *next; struct inpcb inpcb; struct tcpcb tcpcb; @@ -922,18 +966,30 @@ static int conn_read (void) if (status != 0) return (-1); +#if defined(__OpenBSD__) || (defined(__NetBSD_Version__) && __NetBSD_Version__ > 699002700) + /* inpt_queue is a TAILQ on OpenBSD */ + /* Get the first pcb */ + next = (struct inpcb *)TAILQ_FIRST (&table.inpt_queue); + while (next) +#else /* Get the `head' pcb */ head = (struct inpcb *) &(inpcbtable_ptr->inpt_queue); /* Get the first pcb */ next = (struct inpcb *)CIRCLEQ_FIRST (&table.inpt_queue); while (next != head) +#endif { /* Read the pcb pointed to by `next' into `inpcb' */ kread ((u_long) next, &inpcb, sizeof (inpcb)); /* Advance `next' */ +#if defined(__OpenBSD__) || (defined(__NetBSD_Version__) && __NetBSD_Version__ > 699002700) + /* inpt_queue is a TAILQ on OpenBSD */ + next = (struct inpcb *)TAILQ_NEXT (&inpcb, inp_queue); +#else next = (struct inpcb *)CIRCLEQ_NEXT (&inpcb, inp_queue); +#endif /* Ignore sockets, that are not connected. */ #ifdef __NetBSD__