SQM Reporting?

I think that you can directly add interfaces to the single command line.
The script goes through the given interfaces.

option cmdline '/usr/libexec/collectd/sqm_collectd.sh pppoe-wan eth0.2 eth1.3'

I'm quite tempted by


It's a shame that ':punct:' isn't understood.

EDIT: I screwed up my testing, @ldir's approach simply works, I will keep this as a memento mori for myself to actually pay attention first and post later....

That would mean a range from ! to /, to match a literal hyphen, that hypeh need to be in direct contact with one of the square brackets of the pattern definition:


Matches any one of the enclosed characters. A pair of characters separated by a hyphen denotes a range expression; any character that falls between those two characters, inclusive, using the current locale’s collating sequence and character set, is matched. If the first character following the β€˜[’ is a β€˜!’ or a β€˜^’ then any character not enclosed is matched. A β€˜-’ may be matched by including it as the first or last character in the set."

Now this is from bash, and busybox ash might be different, but testing on OpenWrt shows:

root@OpenWrt:~# export ifc="pppoe-wan"
root@ OpenWrt:~# echo $ifc
root@ OpenWrt:~# ifr="${ifc//[-]/_}"
root@ OpenWrt:~# echo $ifr
root@ OpenWrt:~# ifr="${ifc//[\!-|/^@]/_}"
root@ OpenWrt:~# echo $ifr
root@ OpenWrt:~# ifr="${ifc//[-\!|/^@]/_}"
root@ OpenWrt:~# echo $ifr
root@ OpenWrt:~# ifr="${ifc//[.-]/_}"
root@ OpenWrt:~# echo $ifr

So the new more comprehensive pattern seems not to work as desired yet?

So there is the danger of eradicating name differences between different interfaces of they only differ in punctuation, so maybe keep the set of to-be-replaced characters to a minimum?

For the fun of it:

root@nacktmulle:~# ifr="${ifc//[:punct:]/_}"
root@nacktmulle:~# echo $ifr

Bad busybox, :punct: is posix...

root@Router:/mnt/sda3# cat zzz




echo $ifc

echo $ifr

root@Router:/mnt/sda3# ./zzz



Beware the \ escapes!

1 Like

mmmh, that works for me as well:

root@OpenWrt:~# ifc="pppoe-wan"
root@ OpenWrt:~# ifr="${ifc//[\!-\/^@]/_}"
root@ OpenWrt:~# echo $ifr

I screwed up the second "" (backslash) and put in a "|" (pipe) instead, silly me. Sorry for the noise. So much for copy and paste, and then make manual edits...

1 Like

I'm wondering if


is better. It's certainly more readable.

1 Like

+1 for that.

1 Like

Mmmh, if rrdtools only accepts this set, sure, but that still leads the fact that we will be mapping

eth0.2, eth0-2, eth0/2, ... all to eth0_2, which might cause collisions... It probably will not, but the underlaying questions is a set comparison between allowed linux interface names and rrd database identifiers as far as I can tell.
@ldir's approach probably is workable. My preference would be for the [.-] version with an explicit catch for mishandled ones and reporting of these errors to the log instead.

rrdtools isn't the problem (though an interface name of "eth0/2" is alarming) Instead, for cake, the script needs to keep track of the number of sent packets per tin to determine if traffic has actually traversed each tin. It needs to do this across iterations of each interface. The value needs to be preserved per invocation, per interface, per tin.

In any other language you'd probably use an array, something ash doesn't have. The workaround to that is to effectively use dynamic variable names via the joys of 'eval'. A variable for each interface & tin is created. There are, of course, limitations on what constitutes a valid variable name and that is where this limitation is coming from.

Worst case in the case of variable name collision is that data values for latencies & flows are written to the database because 'phantom traffic' has occurred but even then it's not really an issue.

Perfection is the enemy of 'good enough'

1 Like

To use a character class within a character list, you need double brackets:

root@OpenWrt:~# ifc='pppoe-wan!.-@#$%^&*()'
root@OpenWrt:~# echo "${ifc//[[:punct:]]/_}"

Okay, that is great, as that means that we are not length limited. That means even:


and similar would work, making accidental overwriting much more unlikely and the variable names even less attractive, what is not to love in that :wink:

1 Like

Great stuff guys, thx. My dumb question remains... I don't have a web server on most of my boxes at all, how does one go about configuring collectd to toss this at my main logging box, periodically?

You could install collectd-mod-network to both computers and config data to be collected in one computer. Can be done from LuCI, so it is not complicated. That would enable all collectd data to get stored in one computer/router.

1 Like
root@OpenWrt:~# opkg status collectd-mod-exec
Package: collectd-mod-exec
Version: 5.11.0-4
Depends: libc, collectd
Status: install ok installed
Architecture: mipsel_24kc
Installed-Time: 1589045887

root@OpenWrt:~# opkg status collectd
Package: collectd
Version: 5.11.0-4
Depends: libc, libpthread, zlib, libltdl7, libip4tc2, jshn, liblua5.1.5
Status: install user installed
Architecture: mipsel_24kc
 /etc/config/collectd b2599e9fea3d6d5d0aa54f3254b0c3fa37a3559f2836f044732db4e266e83ebc
Installed-Time: 1589045936

root@OpenWrt:~# opkg status rrdtool1
Package: rrdtool1
Version: 1.0.50-3
Depends: libc, librrd1
Status: install ok installed
Architecture: mipsel_24kc
Installed-Time: 1589046355

root@OpenWrt:~# opkg status luci-app-statistics
Package: luci-app-statistics
Version: git-20.128.71843-893dfe7
Depends: libc, luci-base, luci-lib-jsonc, collectd, rrdtool1, collectd-mod-rrdtool, collectd-mod-iwinfo, collectd-mod-cpu, collectd-mod-memory, collectd-mod-interface, collectd-mod-load, collectd-mod-network
Status: install user installed
Architecture: all
 /etc/config/luci_statistics 3932645952d906f5d4ddf5b39c3a36f1f91bc008a31e8dc08b3ab443a0284a35
Installed-Time: 1589046362

root@OpenWrt:~# opkg status collectd-mod-sqm
Package: collectd-mod-sqm
Version: 5.11.0-4
Depends: libc, collectd-mod-exec
Status: install user installed
Architecture: mipsel_24kc
Installed-Time: 1589045887

root@OpenWrt:~# tail /etc/config/luci_statistics

config statistics 'collectd_exec'
        option enable '1'

config collectd_exec_input
        option cmduser 'nobody'
        option cmdgroup 'nogroup'
        option cmdline '/usr/libexec/collectd/sqm_collectd.sh eth0.2'

Getting this error

I guess that you have somehow mixed LuCI component versions. The error comes possibly from luci-base.

You might need to reinstall all main LuCI components to get them in sync.

ok updated all luci components. Now I get this
and I don't know how to configure collectd

Restart LuCI statistics. It piggybacks on collectd and configures it.

Or reboot the router.

Restarted LuCI statistics, rebooted the router... Still same.

Check collectd is running (ps | grep collectd) and check the contents of /tmp/collectd.conf - it should have something like LoadPlugin exec

Exec "nobody:nogroup" "/usr/libexec/collectd/sqm_collectd.sh" "eth0" "ifb4eth0"

If not then try:
service collectd stop
service luci_statistics stop
service luci_statistics start
service collectd start

Also check the rrd data directory exists, is writable and has space:
DataDir "whatever it is"

1 Like