networksensor.cpp
00001 /*************************************************************************** 00002 * Copyright (C) 2003 by Hans Karlsson * 00003 * karlsson.h@home.se * 00004 * * 00005 * This program is free software; you can redistribute it and/or modify * 00006 * it under the terms of the GNU General Public License as published by * 00007 * the Free Software Foundation; either version 2 of the License, or * 00008 * (at your option) any later version. * 00009 ***************************************************************************/ 00010 #ifdef __FreeBSD__ 00011 #include <sys/param.h> 00012 #include <sys/sysctl.h> 00013 #include <sys/socket.h> 00014 #include <net/route.h> 00015 #endif 00016 00017 #include "networksensor.h" 00018 00019 NetworkSensor::NetworkSensor( TQString dev, int interval ):Sensor( interval ) 00020 { 00021 device = dev.lower(); 00022 00023 #ifdef __FreeBSD__ 00024 /* Determine number of interfaces */ 00025 u_int n = 0; 00026 size_t nlen = 0; 00027 nlen = sizeof(n); 00028 sysctlbyname("net.link.generic.system.ifcount", &n, &nlen, NULL, 0); 00029 00030 size_t if_miblen = 0; 00031 if_miblen = sizeof(if_mib); 00032 static int name[] = { CTL_NET, 00033 PF_LINK, 00034 NETLINK_GENERIC, 00035 IFMIB_IFDATA, 00036 0, 00037 IFDATA_GENERAL }; 00038 00039 /* 00040 If the device was defined by the theme, find the right devicenumber. 00041 If not, use the device that holds the default route. 00042 */ 00043 00044 if_number = -1; 00045 int if_gw = -1; 00046 00047 for (int i = 1; i <= n; ++i) { 00048 name[4] = i; 00049 /* Get data for iface-number i */ 00050 sysctl(name, 6, (void*)&if_mib, (size_t*)&if_miblen, (void*)NULL, (size_t)0); 00051 00052 /* We found the right interface? */ 00053 if (TQString(if_mib.ifmd_name) == device) { 00054 if_number = i; 00055 break; 00056 } 00057 00058 /* Does the interface hold the default route? */ 00059 if ( if_mib.ifmd_flags & RTF_GATEWAY ) 00060 if_gw = i; 00061 } 00062 00063 if ((if_number == -1) && (if_gw != -1)) 00064 if_number = if_gw; 00065 #else 00066 if( device.isEmpty() ) 00067 device = "eth0"; 00068 #endif 00069 getInOutBytes(receivedBytes,transmittedBytes); 00070 netTimer.start(); 00071 00072 } 00073 NetworkSensor::~NetworkSensor() 00074 { 00075 } 00076 void NetworkSensor::getInOutBytes ( unsigned long &in,unsigned long &out) const 00077 { 00078 #ifdef __FreeBSD__ 00079 if (if_number != -1) { 00080 size_t if_miblen = 0; 00081 if_miblen = sizeof(if_mib); 00082 int name[] = { CTL_NET, 00083 PF_LINK, 00084 NETLINK_GENERIC, 00085 IFMIB_IFDATA, 00086 if_number, 00087 IFDATA_GENERAL }; 00088 00089 sysctl(name, 6, (void*)&if_mib, (size_t*)&if_miblen, (void*)NULL, (size_t)0); 00090 00091 in = if_mib.ifmd_data.ifi_ibytes; 00092 out = if_mib.ifmd_data.ifi_obytes; 00093 } 00094 else { 00095 in = 0; 00096 out = 0; 00097 } 00098 #else 00099 TQFile file("/proc/net/dev"); 00100 TQString line; 00101 if ( file.open(IO_ReadOnly | IO_Translate) ) 00102 { 00103 TQTextStream t( &file ); // use a text stream 00104 line = t.readLine(); 00105 while(line !=0 && !line.contains(device)) 00106 { 00107 line = t.readLine(); 00108 } 00109 if ( line.contains( device ) ) 00110 { 00111 TQRegExp rx( "\\W+"+device+":\\D*(\\d+)(?:\\D+\\d+){7}\\D+(\\d+)", false); 00112 rx.search(line); 00113 in = rx.cap(1).toULong(); 00114 out = rx.cap(2).toULong(); 00115 } 00116 else 00117 { 00118 qDebug("Network sensor: can not find %s", device.ascii()); 00119 in = 0; 00120 out = 0; 00121 } 00122 file.close(); 00123 } 00124 #endif 00125 } 00126 00127 void NetworkSensor::update() 00128 { 00129 SensorParams *sp; 00130 Meter *meter; 00131 TQObjectListIt it( *objList ); 00132 TQString format; 00133 int decimals; 00134 00135 unsigned long inB, outB; 00136 const double delay = (double) netTimer.elapsed(); // msec elapsed since last update 00137 getInOutBytes( inB, outB ); 00138 netTimer.restart(); 00139 00140 while( it != 0 ) 00141 { 00142 sp = (SensorParams*)(*it); 00143 meter = sp->getMeter(); 00144 format = sp->getParam( "FORMAT" ); 00145 decimals = ( sp->getParam( "DECIMALS" ) ).toInt(); 00146 if (format.length() == 0 ) 00147 { 00148 format = "%in"; 00149 } 00150 00151 format.replace( TQRegExp("%inkb", false), TQString::number( ((inB - receivedBytes)*8)/delay, 'f', decimals ) ); 00152 format.replace( TQRegExp("%in", false), TQString::number( (inB - receivedBytes)/delay, 'f', decimals ) ); 00153 00154 format.replace( TQRegExp("%outkb", false), TQString::number( ((outB - transmittedBytes)*8)/delay, 'f', decimals ) ); 00155 format.replace( TQRegExp("%out", false), TQString::number( (outB - transmittedBytes)/delay, 'f', decimals ) ); 00156 00157 meter->setValue( format ); 00158 ++it; 00159 } 00160 receivedBytes = inB; 00161 transmittedBytes = outB; 00162 } 00163 00164 #include "networksensor.moc"