net_stats: outsource network-related objects
authorPhil Sutter <phil@nwl.cc>
Sat, 17 Oct 2009 14:43:12 +0000 (16:43 +0200)
committerPhil Sutter <phil@nwl.cc>
Tue, 3 Nov 2009 00:50:28 +0000 (01:50 +0100)
13 files changed:
src/Makefile.am
src/common.c
src/common.h
src/conky.c
src/conky.h
src/core.c
src/core.h
src/freebsd.c
src/linux.c
src/net_stat.c [new file with mode: 0644]
src/net_stat.h [new file with mode: 0644]
src/netbsd.c
src/openbsd.c

index f22edda..e12f022 100644 (file)
@@ -51,11 +51,11 @@ endif # BUILD_CONFIG_OUTPUT
 # source files always needed for compiling
 mandatory_sources = colours.c colours.h combine.c combine.h common.c common.h \
                conky.c conky.h core.c core.h diskio.c diskio.h exec.c exec.h fs.c \
-               fs.h logging.h mail.c mail.h mixer.c mixer.h template.c template.h \
-               timed_thread.c timed_thread.h mboxscan.c mboxscan.h read_tcp.c \
-               read_tcp.h scroll.c scroll.h specials.c specials.h tailhead.c \
-               tailhead.h temphelper.c temphelper.h text_object.c text_object.h \
-               timeinfo.c timeinfo.h algebra.c algebra.h
+               fs.h logging.h mail.c mail.h mixer.c mixer.h net_stat.c net_stat.h \
+               template.c template.h timed_thread.c timed_thread.h mboxscan.c \
+               mboxscan.h read_tcp.c read_tcp.h scroll.c scroll.h specials.c \
+               specials.h tailhead.c tailhead.h temphelper.c temphelper.h \
+               text_object.c text_object.h timeinfo.c timeinfo.h algebra.c algebra.h
 
 # source files only needed when the apropriate option is enabled
 audacious = audacious.c audacious.h
index eb61b72..160f23c 100644 (file)
@@ -32,6 +32,7 @@
 #include "conky.h"
 #include "fs.h"
 #include "logging.h"
+#include "net_stat.h"
 #include <ctype.h>
 #include <errno.h>
 #include <sys/time.h>
@@ -211,135 +212,6 @@ void variable_substitute(const char *s, char *dest, unsigned int n)
        *dest = '\0';
 }
 
-/* network interface stuff */
-
-static struct net_stat netstats[16];
-
-struct net_stat *get_net_stat(const char *dev, void *free_at_crash1, void *free_at_crash2)
-{
-       unsigned int i;
-
-       if (!dev) {
-               return 0;
-       }
-
-       /* find interface stat */
-       for (i = 0; i < 16; i++) {
-               if (netstats[i].dev && strcmp(netstats[i].dev, dev) == 0) {
-                       return &netstats[i];
-               }
-       }
-
-       /* wasn't found? add it */
-       for (i = 0; i < 16; i++) {
-               if (netstats[i].dev == 0) {
-                       netstats[i].dev = strndup(dev, text_buffer_size);
-                       return &netstats[i];
-               }
-       }
-
-       CRIT_ERR(free_at_crash1, free_at_crash2, "too many interfaces used (limit is 16)");
-       return 0;
-}
-
-void clear_net_stats(void)
-{
-       int i;
-       for (i = 0; i < 16; i++) {
-               if (netstats[i].dev) {
-                       free(netstats[i].dev);
-               }
-       }
-       memset(netstats, 0, sizeof(netstats));
-}
-
-/* We should check if this is ok with OpenBSD and NetBSD as well. */
-int interface_up(const char *dev)
-{
-       int fd;
-       struct ifreq ifr;
-
-       if ((fd = socket(PF_INET, SOCK_DGRAM, 0)) < 0) {
-               CRIT_ERR(NULL, NULL, "could not create sockfd");
-               return 0;
-       }
-       strncpy(ifr.ifr_name, dev, IFNAMSIZ);
-       if (ioctl(fd, SIOCGIFFLAGS, &ifr)) {
-               /* if device does not exist, treat like not up */
-               if (errno != ENODEV && errno != ENXIO)
-                       perror("SIOCGIFFLAGS");
-               goto END_FALSE;
-       }
-
-       if (!(ifr.ifr_flags & IFF_UP)) /* iface is not up */
-               goto END_FALSE;
-       if (ifup_strictness == IFUP_UP)
-               goto END_TRUE;
-
-       if (!(ifr.ifr_flags & IFF_RUNNING))
-               goto END_FALSE;
-       if (ifup_strictness == IFUP_LINK)
-               goto END_TRUE;
-
-       if (ioctl(fd, SIOCGIFADDR, &ifr)) {
-               perror("SIOCGIFADDR");
-               goto END_FALSE;
-       }
-       if (((struct sockaddr_in *)&(ifr.ifr_ifru.ifru_addr))->sin_addr.s_addr)
-               goto END_TRUE;
-
-END_FALSE:
-       close(fd);
-       return 0;
-END_TRUE:
-       close(fd);
-       return 1;
-}
-
-void free_dns_data(void)
-{
-       int i;
-       struct dns_data *data = &info.nameserver_info;
-       for (i = 0; i < data->nscount; i++)
-               free(data->ns_list[i]);
-       if (data->ns_list)
-               free(data->ns_list);
-       memset(data, 0, sizeof(struct dns_data));
-}
-
-//static double last_dns_update;
-
-void update_dns_data(void)
-{
-       FILE *fp;
-       char line[256];
-       struct dns_data *data = &info.nameserver_info;
-
-       /* maybe updating too often causes higher load because of /etc lying on a real FS
-       if (current_update_time - last_dns_update < 10.0)
-               return;
-       else
-               last_dns_update = current_update_time;
-       */
-
-       free_dns_data();
-
-       if ((fp = fopen("/etc/resolv.conf", "r")) == NULL)
-               return;
-       while(!feof(fp)) {
-               if (fgets(line, 255, fp) == NULL) {
-                       break;
-               }
-               if (!strncmp(line, "nameserver ", 11)) {
-                       line[strlen(line) - 1] = '\0';  // remove trailing newline
-                       data->nscount++;
-                       data->ns_list = realloc(data->ns_list, data->nscount * sizeof(char *));
-                       data->ns_list[data->nscount - 1] = strndup(line + 11, text_buffer_size);
-               }
-       }
-       fclose(fp);
-}
-
 void format_seconds(char *buf, unsigned int n, long seconds)
 {
        long days;
index d39d156..33d9d1d 100644 (file)
@@ -18,7 +18,6 @@ void start_update_threading(void);
 void strfold(char *start, int count);
 int check_mount(char *s);
 void prepare_update(void);
-void update_dns_data(void);
 void update_uptime(void);
 void update_meminfo(void);
 void update_net_stats(void);
@@ -59,35 +58,6 @@ unsigned int round_to_int(float);
 
 extern int no_buffers;
 
-struct dns_data {
-        int nscount;
-        char **ns_list;
-};
-void free_dns_data(void);
-
-struct net_stat {
-        char *dev;
-        int up;
-        long long last_read_recv, last_read_trans;
-        long long recv, trans;
-        double recv_speed, trans_speed;
-        struct sockaddr addr;
-#if defined(__linux__)
-        char addrs[273];
-#endif /* __linux__ */
-        double net_rec[15], net_trans[15];
-        // wireless extensions
-        char essid[32];
-        char bitrate[16];
-        char mode[16];
-        int link_qual;
-        int link_qual_max;
-        char ap[18];
-};
-void clear_net_stats(void);
-struct net_stat *get_net_stat(const char *dev, void *free_at_crash1, void *free_at_crash2);
-int interface_up(const char *dev);
-
 void get_adt746x_cpu(char *, size_t);
 void get_adt746x_fan(char *, size_t);
 
index fb235fa..db88a3c 100644 (file)
@@ -89,6 +89,7 @@
 #include "mixer.h"
 #include "mail.h"
 #include "mboxscan.h"
+#include "net_stat.h"
 #include "read_tcp.h"
 #include "scroll.h"
 #include "specials.h"
@@ -924,47 +925,28 @@ void generate_text_internal(char *p, int p_max_size,
 
 #ifdef HAVE_IWLIB
                        OBJ(wireless_essid) {
-                               snprintf(p, p_max_size, "%s", obj->data.net->essid);
+                               print_wireless_essid(obj, p, p_max_size);
                        }
                        OBJ(wireless_mode) {
-                               snprintf(p, p_max_size, "%s", obj->data.net->mode);
+                               print_wireless_mode(obj, p, p_max_size);
                        }
                        OBJ(wireless_bitrate) {
-                               snprintf(p, p_max_size, "%s", obj->data.net->bitrate);
+                               print_wireless_bitrate(obj, p, p_max_size);
                        }
                        OBJ(wireless_ap) {
-                               snprintf(p, p_max_size, "%s", obj->data.net->ap);
+                               print_wireless_ap(obj, p, p_max_size);
                        }
                        OBJ(wireless_link_qual) {
-                               spaced_print(p, p_max_size, "%d", 4,
-                                               obj->data.net->link_qual);
+                               print_wireless_link_qual(obj, p, p_max_size);
                        }
                        OBJ(wireless_link_qual_max) {
-                               spaced_print(p, p_max_size, "%d", 4,
-                                               obj->data.net->link_qual_max);
+                               print_wireless_link_qual_max(obj, p, p_max_size);
                        }
                        OBJ(wireless_link_qual_perc) {
-                               if (obj->data.net->link_qual_max > 0) {
-                                       spaced_print(p, p_max_size, "%.0f", 5,
-                                                       (double) obj->data.net->link_qual /
-                                                       obj->data.net->link_qual_max * 100);
-                               } else {
-                                       spaced_print(p, p_max_size, "unk", 5);
-                               }
+                               print_wireless_link_qual_perc(obj, p, p_max_size);
                        }
                        OBJ(wireless_link_bar) {
-#ifdef X11
-                               if(output_methods & TO_X) {
-                                       new_bar(p, obj->a, obj->b, ((double) obj->data.net->link_qual /
-                                               obj->data.net->link_qual_max) * 255.0);
-                               }else{
-#endif /* X11 */
-                                       if(!obj->a) obj->a = DEFAULT_BAR_WIDTH_NO_X;
-                                       new_bar_in_shell(p, p_max_size, ((double) obj->data.net->link_qual /
-                                               obj->data.net->link_qual_max) * 100.0, obj->a);
-#ifdef X11
-                               }
-#endif /* X11 */
+                               print_wireless_link_bar(obj, p, p_max_size);
                        }
 #endif /* HAVE_IWLIB */
 
@@ -1275,16 +1257,14 @@ void generate_text_internal(char *p, int p_max_size,
                        }
 #endif /* X11 */
                        OBJ(downspeed) {
-                               human_readable(obj->data.net->recv_speed, p, 255);
+                               print_downspeed(obj, p, p_max_size);
                        }
                        OBJ(downspeedf) {
-                               spaced_print(p, p_max_size, "%.1f", 8,
-                                               obj->data.net->recv_speed / 1024.0);
+                               print_downspeedf(obj, p, p_max_size);
                        }
 #ifdef X11
                        OBJ(downspeedgraph) {
-                               new_graph(p, obj->a, obj->b, obj->c, obj->d,
-                                       obj->data.net->recv_speed / 1024.0, obj->e, 1, obj->char_a, obj->char_b);
+                               print_downspeedgraph(obj, p);
                        }
 #endif /* X11 */
                        OBJ(else) {
@@ -1299,27 +1279,11 @@ void generate_text_internal(char *p, int p_max_size,
                                /* harmless object, just ignore */
                        }
                        OBJ(addr) {
-                               if ((obj->data.net->addr.sa_data[2] & 255) == 0
-                                               && (obj->data.net->addr.sa_data[3] & 255) == 0
-                                               && (obj->data.net->addr.sa_data[4] & 255) == 0
-                                               && (obj->data.net->addr.sa_data[5] & 255) == 0) {
-                                       snprintf(p, p_max_size, "No Address");
-                               } else {
-                                       snprintf(p, p_max_size, "%u.%u.%u.%u",
-                                               obj->data.net->addr.sa_data[2] & 255,
-                                               obj->data.net->addr.sa_data[3] & 255,
-                                               obj->data.net->addr.sa_data[4] & 255,
-                                               obj->data.net->addr.sa_data[5] & 255);
-                               }
+                               print_addr(obj, p, p_max_size);
                        }
 #if defined(__linux__)
                        OBJ(addrs) {
-                               if (NULL != obj->data.net->addrs && strlen(obj->data.net->addrs) > 2) {
-                                       obj->data.net->addrs[strlen(obj->data.net->addrs) - 2] = 0; /* remove ", " from end of string */
-                                       strcpy(p, obj->data.net->addrs);
-                               } else {
-                                       strcpy(p, "0.0.0.0");
-                               }
+                               print_addrs(obj, p, p_max_size);
                        }
 #endif /* __linux__ */
 #if defined(IMLIB2) && defined(X11)
@@ -1487,9 +1451,7 @@ void generate_text_internal(char *p, int p_max_size,
                        }
 #endif
                        OBJ(nameserver) {
-                               if (cur->nameserver_info.nscount > obj->data.i)
-                                       snprintf(p, p_max_size, "%s",
-                                                       cur->nameserver_info.ns_list[obj->data.i]);
+                               print_nameserver(obj, p, p_max_size);
                        }
 #ifdef EVE
                        OBJ(eve) {
@@ -1909,10 +1871,10 @@ void generate_text_internal(char *p, int p_max_size,
                                print_tztime(obj, p, p_max_size);
                        }
                        OBJ(totaldown) {
-                               human_readable(obj->data.net->recv, p, 255);
+                               print_totaldown(obj, p, p_max_size);
                        }
                        OBJ(totalup) {
-                               human_readable(obj->data.net->trans, p, 255);
+                               print_totalup(obj, p, p_max_size);
                        }
                        OBJ(updates) {
                                snprintf(p, p_max_size, "%d", total_updates);
@@ -1923,16 +1885,14 @@ void generate_text_internal(char *p, int p_max_size,
                                }
                        }
                        OBJ(upspeed) {
-                               human_readable(obj->data.net->trans_speed, p, 255);
+                               print_upspeed(obj, p, p_max_size);
                        }
                        OBJ(upspeedf) {
-                               spaced_print(p, p_max_size, "%.1f", 8,
-                                       obj->data.net->trans_speed / 1024.0);
+                               print_upspeedf(obj, p, p_max_size);
                        }
 #ifdef X11
                        OBJ(upspeedgraph) {
-                               new_graph(p, obj->a, obj->b, obj->c, obj->d,
-                                       obj->data.net->trans_speed / 1024.0, obj->e, 1, obj->char_a, obj->char_b);
+                               print_upspeedgraph(obj, p);
                        }
 #endif /* X11 */
                        OBJ(uptime_short) {
index 62a4ac3..3318331 100644 (file)
@@ -256,7 +256,6 @@ struct information {
        struct bmpx_s bmpx;
 #endif
        struct usr_info users;
-       struct dns_data nameserver_info;
        struct process *cpu[10];
        struct process *memu[10];
        struct process *time[10];
index 4db44ea..36d1e34 100644 (file)
@@ -48,6 +48,7 @@
 #include "mixer.h"
 #include "mail.h"
 #include "mboxscan.h"
+#include "net_stat.h"
 #include "read_tcp.h"
 #include "scroll.h"
 #include "specials.h"
@@ -82,7 +83,7 @@ void update_entropy(void);
  *         which gets overwritten in consecutive calls. I.e.:
  *         this function is NOT reentrant.
  */
-static const char *dev_name(const char *path)
+const char *dev_name(const char *path)
 {
        static char buf[255];   /* should be enough for pathnames */
        ssize_t buflen;
@@ -206,79 +207,21 @@ struct text_object *construct_text_object(const char *s, const char *arg, long
 
 #ifdef HAVE_IWLIB
        END OBJ(wireless_essid, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(wireless_mode, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(wireless_bitrate, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(wireless_ap, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(wireless_link_qual, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(wireless_link_qual_max, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(wireless_link_qual_perc, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(wireless_link_bar, &update_net_stats)
-               SIZE_DEFAULTS(bar);
-               if (arg) {
-                       arg = scan_bar(arg, &obj->a, &obj->b);
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_bar_arg(obj, arg, free_at_crash);
 #endif /* HAVE_IWLIB */
 
 #endif /* __linux__ */
@@ -550,34 +493,12 @@ struct text_object *construct_text_object(const char *s, const char *arg, long
        END OBJ(conky_build_date, 0)
        END OBJ(conky_build_arch, 0)
        END OBJ(downspeed, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(downspeedf, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
 #ifdef X11
        END OBJ(downspeedgraph, &update_net_stats)
-               char *buf = 0;
-               SIZE_DEFAULTS(graph);
-               buf = scan_graph(arg, &obj->a, &obj->b, &obj->c, &obj->d,
-                               &obj->e, &obj->char_a, &obj->char_b);
-
-               // default to DEFAULTNETDEV
-               buf = strndup(buf ? buf : DEFAULTNETDEV, text_buffer_size);
-               obj->data.net = get_net_stat(buf, obj, free_at_crash);
-               free(buf);
+               parse_net_stat_graph_arg(obj, arg, free_at_crash);
 #endif /* X11 */
        END OBJ(else, 0)
                obj_be_ifblock_else(ifblock_opaque, obj);
@@ -660,7 +581,7 @@ struct text_object *construct_text_object(const char *s, const char *arg, long
        END OBJ(hr, 0)
                obj->data.i = arg ? atoi(arg) : 1;
        END OBJ(nameserver, &update_dns_data)
-               obj->data.i = arg ? atoi(arg) : 0;
+               parse_nameserver_arg(obj, arg);
        END OBJ(offset, 0)
                obj->data.i = arg ? atoi(arg) : 1;
        END OBJ(voffset, 0)
@@ -701,24 +622,10 @@ struct text_object *construct_text_object(const char *s, const char *arg, long
                        return NULL;
                }
        } else OBJ(addr, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
 #if defined(__linux__)
        END OBJ(addrs, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
 #endif /* __linux__ */
        END OBJ_ARG(tail, 0, "tail needs arguments")
                init_tailhead("tail", arg, obj, free_at_crash);
@@ -1094,24 +1001,9 @@ struct text_object *construct_text_object(const char *s, const char *arg, long
                init_iconv_stop();
 #endif
        END OBJ(totaldown, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(totalup, &update_net_stats)
-               obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(updates, 0)
        END OBJ_IF(if_updatenr, 0)
                obj->data.ifblock.i = arg ? atoi(arg) : 0;
@@ -1122,35 +1014,12 @@ struct text_object *construct_text_object(const char *s, const char *arg, long
        END OBJ(alignc, 0)
                obj->data.i = arg ? atoi(arg) : 0;
        END OBJ(upspeed, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
+               parse_net_stat_arg(obj, arg, free_at_crash);
        END OBJ(upspeedf, &update_net_stats)
-               if (arg) {
-                       obj->data.net = get_net_stat(arg, obj, free_at_crash);
-               } else {
-                       // default to DEFAULTNETDEV
-                       char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
-                       obj->data.net = get_net_stat(buf, obj, free_at_crash);
-                       free(buf);
-               }
-
+               parse_net_stat_arg(obj, arg, free_at_crash);
 #ifdef X11
        END OBJ(upspeedgraph, &update_net_stats)
-               char *buf = 0;
-               SIZE_DEFAULTS(graph);
-               buf = scan_graph(arg, &obj->a, &obj->b, &obj->c, &obj->d,
-                               &obj->e, &obj->char_a, &obj->char_b);
-
-               // default to DEFAULTNETDEV
-               buf = strndup(buf ? buf : DEFAULTNETDEV, text_buffer_size);
-               obj->data.net = get_net_stat(buf, obj, free_at_crash);
-               free(buf);
+               parse_net_stat_graph_arg(obj, arg, free_at_crash);
 #endif
        END OBJ(uptime_short, &update_uptime)
        END OBJ(uptime, &update_uptime)
index 1d1c140..da1aa25 100644 (file)
@@ -46,4 +46,6 @@ void free_text_objects(struct text_object *root, int internal);
 void scan_mixer_bar(const char *arg, int *a, int *w, int *h);
 #endif /* X11 */
 
+const char *dev_name(const char *);
+
 #endif /* _CONKY_CORE_H_ */
index 7f58eb7..736b394 100644 (file)
@@ -54,6 +54,7 @@
 #include "conky.h"
 #include "freebsd.h"
 #include "logging.h"
+#include "net_stat.h"
 #include "top.h"
 #include "diskio.h"
 
index 0c85a12..e1deceb 100644 (file)
@@ -33,6 +33,7 @@
 #include "logging.h"
 #include "common.h"
 #include "linux.h"
+#include "net_stat.h"
 #include "diskio.h"
 #include "temphelper.h"
 #include <dirent.h>
diff --git a/src/net_stat.c b/src/net_stat.c
new file mode 100644 (file)
index 0000000..59ecf47
--- /dev/null
@@ -0,0 +1,401 @@
+/* -*- mode: c; c-basic-offset: 4; tab-width: 4; indent-tabs-mode: t -*-
+ * vim: ts=4 sw=4 noet ai cindent syntax=c
+ *
+ * Conky, a system monitor, based on torsmo
+ *
+ * Any original torsmo code is licensed under the BSD license
+ *
+ * All code written since the fork of torsmo is licensed under the GPL
+ *
+ * Please see COPYING for details
+ *
+ * Copyright (c) 2004, Hannu Saransaari and Lauri Hakkarainen
+ * Copyright (c) 2005-2009 Brenden Matthews, Philip Kovacs, et. al.
+ *     (see AUTHORS)
+ * All rights reserved.
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ *
+ */
+
+#include "config.h"
+#include "logging.h"
+#include "specials.h"
+#include "net/if.h"
+#include "text_object.h"
+#include "net_stat.h"
+#include <errno.h>
+#include <string.h>
+#include <sys/ioctl.h>
+
+/* network interface stuff */
+
+struct net_stat netstats[16];
+
+struct net_stat *get_net_stat(const char *dev, void *free_at_crash1, void *free_at_crash2)
+{
+       unsigned int i;
+
+       if (!dev) {
+               return 0;
+       }
+
+       /* find interface stat */
+       for (i = 0; i < 16; i++) {
+               if (netstats[i].dev && strcmp(netstats[i].dev, dev) == 0) {
+                       return &netstats[i];
+               }
+       }
+
+       /* wasn't found? add it */
+       for (i = 0; i < 16; i++) {
+               if (netstats[i].dev == 0) {
+                       netstats[i].dev = strndup(dev, text_buffer_size);
+                       return &netstats[i];
+               }
+       }
+
+       CRIT_ERR(free_at_crash1, free_at_crash2, "too many interfaces used (limit is 16)");
+       return 0;
+}
+
+void parse_net_stat_arg(struct text_object *obj, const char *arg, void *free_at_crash)
+{
+       if (!arg)
+               arg = DEFAULTNETDEV;
+
+       obj->data.net = get_net_stat(arg, obj, free_at_crash);
+}
+
+void parse_net_stat_bar_arg(struct text_object *obj, const char *arg, void *free_at_crash)
+{
+       SIZE_DEFAULTS(bar);
+       if (arg) {
+               arg = scan_bar(arg, &obj->a, &obj->b);
+               obj->data.net = get_net_stat(arg, obj, free_at_crash);
+       } else {
+               // default to DEFAULTNETDEV
+               char *buf = strndup(DEFAULTNETDEV, text_buffer_size);
+               obj->data.net = get_net_stat(buf, obj, free_at_crash);
+               free(buf);
+       }
+}
+
+void print_downspeed(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       human_readable(obj->data.net.recv_speed, p, p_max_size);
+}
+
+void print_downspeedf(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       spaced_print(p, p_max_size, "%.1f", 8, obj->data.netrecv_speed / 1024.0);
+}
+
+void print_upspeed(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       human_readable(obj->data.net.trans_speed, p, p_max_size);
+}
+
+void print_upspeedf(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       spaced_print(p, p_max_size, "%.1f", 8, obj->data.net.trans_speed / 1024.0);
+}
+
+void print_totaldown(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       human_readable(obj->data.net.recv, p, p_max_size);
+}
+
+void print_totalup(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       human_readable(obj->data.net.trans, p, p_max_size);
+}
+
+void print_addr(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       if ((obj->data.net.addr.sa_data[2] & 255) == 0 &&
+           (obj->data.net.addr.sa_data[3] & 255) == 0 &&
+           (obj->data.net.addr.sa_data[4] & 255) == 0 &&
+           (obj->data.net.addr.sa_data[5] & 255) == 0) {
+               snprintf(p, p_max_size, "No Address");
+       } else {
+               snprintf(p, p_max_size, "%u.%u.%u.%u",
+                        obj->data.net.addr.sa_data[2] & 255,
+                        obj->data.net.addr.sa_data[3] & 255,
+                        obj->data.net.addr.sa_data[4] & 255,
+                        obj->data.net.addr.sa_data[5] & 255);
+       }
+}
+
+#ifdef __linux__
+void print_addrs(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       if (NULL != obj->data.net.addrs && strlen(obj->data.net.addrs) > 2) {
+               obj->data.net.addrs[strlen(obj->data.net.addrs) - 2] = 0; /* remove ", " from end of string */
+               strncpy(p, obj->data.net.addrs, p_max_size);
+       } else {
+               strncpy(p, "0.0.0.0", p_max_size);
+       }
+}
+#endif /* __linux__ */
+
+#ifdef X11
+void parse_net_stat_graph_arg(struct text_object *obj, const char *arg, void *free_at_crash)
+{
+       char *buf = 0;
+       SIZE_DEFAULTS(graph);
+       buf = scan_graph(arg, &obj->a, &obj->b, &obj->c, &obj->d,
+                       &obj->e, &obj->char_a, &obj->char_b);
+
+       // default to DEFAULTNETDEV
+       if (buf) {
+               obj->data.net = get_net_stat(buf, obj, free_at_crash);
+               free(buf);
+               return;
+       }
+       obj->data.net = get_net_stat(DEFAULTNETDEV, obj, free_at_crash);
+}
+
+void print_downspeedgraph(struct text_object *obj, char *p)
+{
+       if (!obj->data.net)
+               return;
+
+       new_graph(p, obj->a, obj->b, obj->c, obj->d,
+                       obj->data.net.recv_speed / 1024.0, obj->e, 1, obj->char_a, obj->char_b);
+}
+
+void print_upspeedgraph(struct text_object *obj, char *p)
+{
+       if (!obj->data.net)
+               return;
+
+       new_graph(p, obj->a, obj->b, obj->c, obj->d,
+                       obj->data.net.trans_speed / 1024.0, obj->e, 1, obj->char_a, obj->char_b);
+}
+#endif /* X11 */
+
+#ifdef __linux__
+#ifdef HAVE_IWLIB
+void print_wireless_essid(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       snprintf(p, p_max_size, "%s", obj->data.net.essid);
+}
+void print_wireless_mode(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       snprintf(p, p_max_size, "%s", obj->data.net.mode);
+}
+void print_wireless_bitrate(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       snprintf(p, p_max_size, "%s", obj->data.net.bitrate);
+}
+void print_wireless_ap(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       snprintf(p, p_max_size, "%s", obj->data.net.ap);
+}
+void print_wireless_link_qual(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       spaced_print(p, p_max_size, "%d", 4, obj->data.net.link_qual);
+}
+void print_wireless_link_qual_max(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       spaced_print(p, p_max_size, "%d", 4, obj->data.net.link_qual_max);
+}
+void print_wireless_link_qual_perc(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+       if (obj->data.net.link_qual_max > 0) {
+               spaced_print(p, p_max_size, "%.0f", 5,
+                               (double) obj->data.net.link_qual /
+                               obj->data.net.link_qual_max * 100);
+       } else {
+               spaced_print(p, p_max_size, "unk", 5);
+       }
+}
+void print_wireless_link_bar(struct text_object *obj, char *p, int p_max_size)
+{
+       if (!obj->data.net)
+               return;
+
+#ifdef X11
+       if(output_methods & TO_X) {
+               new_bar(p, obj->a, obj->b, ((double) obj->data.net.link_qual /
+                                       obj->data.net.link_qual_max) * 255.0);
+       } else
+#endif /* X11 */
+       {
+               if(!obj->a) obj->a = DEFAULT_BAR_WIDTH_NO_X;
+               new_bar_in_shell(p, p_max_size, ((double) obj->data.net.link_qual /
+                                       obj->data.net.link_qual_max) * 100.0, obj->a);
+       }
+}
+#endif /* HAVE_IWLIB */
+#endif /* __linux__ */
+
+void clear_net_stats(void)
+{
+       int i;
+       for (i = 0; i < 16; i++) {
+               if (netstats[i].dev) {
+                       free(netstats[i].dev);
+               }
+       }
+       memset(netstats, 0, sizeof(netstats));
+}
+
+/* We should check if this is ok with OpenBSD and NetBSD as well. */
+int interface_up(const char *dev)
+{
+       int fd;
+       struct ifreq ifr;
+
+       if ((fd = socket(PF_INET, SOCK_DGRAM, 0)) < 0) {
+               CRIT_ERR(NULL, NULL, "could not create sockfd");
+               return 0;
+       }
+       strncpy(ifr.ifr_name, dev, IFNAMSIZ);
+       if (ioctl(fd, SIOCGIFFLAGS, &ifr)) {
+               /* if device does not exist, treat like not up */
+               if (errno != ENODEV && errno != ENXIO)
+                       perror("SIOCGIFFLAGS");
+               goto END_FALSE;
+       }
+
+       if (!(ifr.ifr_flags & IFF_UP)) /* iface is not up */
+               goto END_FALSE;
+       if (ifup_strictness == IFUP_UP)
+               goto END_TRUE;
+
+       if (!(ifr.ifr_flags & IFF_RUNNING))
+               goto END_FALSE;
+       if (ifup_strictness == IFUP_LINK)
+               goto END_TRUE;
+
+       if (ioctl(fd, SIOCGIFADDR, &ifr)) {
+               perror("SIOCGIFADDR");
+               goto END_FALSE;
+       }
+       if (((struct sockaddr_in *)&(ifr.ifr_ifru.ifru_addr))->sin_addr.s_addr)
+               goto END_TRUE;
+
+END_FALSE:
+       close(fd);
+       return 0;
+END_TRUE:
+       close(fd);
+       return 1;
+}
+
+static struct {
+        int nscount;
+        char **ns_list;
+} dns_data = {
+       .nscount = 0,
+       .ns_list = NULL,
+};
+
+void free_dns_data(void)
+{
+       int i;
+       for (i = 0; i < dns_data.nscount; i++)
+               free(dns_data.ns_list[i]);
+       if (dns_data.ns_list)
+               free(dns_data.ns_list);
+       memset(&dns_data, 0, sizeof(dns_data));
+}
+
+void update_dns_data(void)
+{
+       FILE *fp;
+       char line[256];
+       //static double last_dns_update = 0.0;
+
+       /* maybe updating too often causes higher load because of /etc lying on a real FS
+       if (current_update_time - last_dns_update < 10.0)
+               return;
+
+       last_dns_update = current_update_time;
+       */
+
+       free_dns_data();
+
+       if ((fp = fopen("/etc/resolv.conf", "r")) == NULL)
+               return;
+       while(!feof(fp)) {
+               if (fgets(line, 255, fp) == NULL) {
+                       break;
+               }
+               if (!strncmp(line, "nameserver ", 11)) {
+                       line[strlen(line) - 1] = '\0';  // remove trailing newline
+                       dns_data.nscount++;
+                       dns_data.ns_list = realloc(dns_data.ns_list, dns_data.nscount * sizeof(char *));
+                       dns_data.ns_list[dns_data.nscount - 1] = strndup(line + 11, text_buffer_size);
+               }
+       }
+       fclose(fp);
+}
+
+void parse_nameserver_arg(struct text_object *obj, const char *arg)
+{
+       obj->data.l = arg ? atoi(arg) : 0;
+}
+
+void print_nameserver(struct text_object *obj, char *p, int p_max_size)
+{
+       if (dns_data.nscount > obj->data.l)
+               snprintf(p, p_max_size, "%s", dns_data.ns_list[obj->data.l]);
+}
diff --git a/src/net_stat.h b/src/net_stat.h
new file mode 100644 (file)
index 0000000..af3ba97
--- /dev/null
@@ -0,0 +1,98 @@
+/* -*- mode: c; c-basic-offset: 4; tab-width: 4; indent-tabs-mode: t -*-
+ * vim: ts=4 sw=4 noet ai cindent syntax=c
+ *
+ * Conky, a system monitor, based on torsmo
+ *
+ * Any original torsmo code is licensed under the BSD license
+ *
+ * All code written since the fork of torsmo is licensed under the GPL
+ *
+ * Please see COPYING for details
+ *
+ * Copyright (c) 2004, Hannu Saransaari and Lauri Hakkarainen
+ * Copyright (c) 2005-2009 Brenden Matthews, Philip Kovacs, et. al.
+ *     (see AUTHORS)
+ * All rights reserved.
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ *
+ */
+
+#ifndef _NET_STAT_H
+#define _NET_STAT_H
+
+#include <sys/socket.h>        /* struct sockaddr */
+
+struct net_stat {
+        char *dev;
+        int up;
+        long long last_read_recv, last_read_trans;
+        long long recv, trans;
+        double recv_speed, trans_speed;
+        struct sockaddr addr;
+#if defined(__linux__)
+        char addrs[273];
+#endif /* __linux__ */
+        double net_rec[15], net_trans[15];
+        // wireless extensions
+        char essid[32];
+        char bitrate[16];
+        char mode[16];
+        int link_qual;
+        int link_qual_max;
+        char ap[18];
+};
+
+extern struct net_stat netstats[];
+
+struct net_stat *get_net_stat(const char *, void *, void *);
+
+void parse_net_stat_arg(struct text_object *, const char *, void *);
+void parse_net_stat_bar_arg(struct text_object *, const char *, void *);
+void print_downspeed(struct text_object *, char *, int);
+void print_downspeedf(struct text_object *, char *, int);
+void print_upspeed(struct text_object *, char *, int);
+void print_upspeedf(struct text_object *, char *, int);
+void print_totaldown(struct text_object *, char *, int);
+void print_totalup(struct text_object *, char *, int);
+void print_addr(struct text_object *, char *, int);
+#ifdef __linux__
+void print_addrs(struct text_object *, char *, int);
+#endif /* __linux__ */
+#ifdef X11
+void parse_net_stat_graph_arg(struct text_object *, const char *, void *);
+void print_downspeedgraph(struct text_object *, char *);
+void print_upspeedgraph(struct text_object *, char *);
+#endif /* X11 */
+#ifdef __linux__
+#ifdef HAVE_IWLIB
+void print_wireless_essid(struct text_object *, char *, int);
+void print_wireless_mode(struct text_object *, char *, int);
+void print_wireless_bitrate(struct text_object *, char *, int);
+void print_wireless_ap(struct text_object *, char *, int);
+void print_wireless_link_qual(struct text_object *, char *, int);
+void print_wireless_link_qual_max(struct text_object *, char *, int);
+void print_wireless_link_qual_perc(struct text_object *, char *, int);
+void print_wireless_link_bar(struct text_object *, char *, int);
+#endif /* HAVE_IWLIB */
+#endif /* __linux__ */
+
+void clear_net_stats(void);
+int interface_up(const char *);
+
+void free_dns_data(void);
+void update_dns_data(void);
+void parse_nameserver_arg(struct text_object *, const char *);
+void print_nameserver(struct text_object *, char *, int);
+
+#endif /* _NET_STAT_H */
index ccc7ebe..dc4e0f7 100644 (file)
@@ -29,6 +29,7 @@
  */
 
 #include "netbsd.h"
+#include "net_stat.h"
 
 static kvm_t *kd = NULL;
 int kd_init = 0, nkd_init = 0;
index bcbe072..4d5f240 100644 (file)
@@ -61,6 +61,7 @@
 #include "conky.h"
 #include "diskio.h"
 #include "logging.h"
+#include "net_stat.h"
 #include "openbsd.h"
 #include "top.h"