I’m in the process of migrating to a different ISP. Whereas until now I have been on a flat rate for download usage, the new provider charges significantly more for downloads between 0900 and 1800 on weekdays.
As I have a Cisco 877 router I should be able to throttle downloads during peak times and save myself money compared to the plan I’ve been using.
Note that the ISP doesn’t charge for excessive upload so my work was focussed 100% on download throttling.
The first thing to do was set up a time-range so the router knows what peak time is. Well actually the zeroth thing to do was configure my timezone correctly.
clock timezone GMT 0 clock summer-time BST recurring last Sun Mar 1:00 last sun Oct 2:00
Now I could define the time range.
time-range peak periodic weekdays 9:00 to 17:59
Just for fun I set up an off-peak time range.
time-range off-peak periodic weekdays 0:00 to 8:59 periodic weekdays 18:00 to 23:59 periodic weekend 0:00 to 23:59
The sh time-range command verifies that these are set up.
# sh time-range time-range entry: off-peak (active) periodic weekdays 0:00 to 8:59 periodic weekdays 18:00 to 23:59 periodic weekend 0:00 to 23:59 time-range entry: peak (inactive) periodic weekdays 9:00 to 17:59
The off-peak range shows as active which is correct because it’s Sunday at time of writing.
Next I created an access list which would match any connection at peak time.
ip access-list extended peak permit ip any any time-range peak
At this point I could have just set things up so downloads were throttled at peak times but that would have been inelegant and I wanted more control. For instance Rebecca will be at home working during the day and she wants to be able to download her mail and make calls to China with Skype. So for want of a better idea I decided to set up five usage categories:
Default Anything I forget about and don’t fit into one of the subsequent categories. Limited to 64kbps.
Lowest: Stuff that has no business running during the day, like Bittorrent. Limited to 32kbps.
Low: Stuff like Steam automatic downloads and SSH. Limited to 128kbps.
Medium: Stuff which could well run during the day and which shouldn’t be horrendously slow but which I don’t want spiralling out of control. Skype and HTTP for example. Limited to 256kbps.
High: For things that gotta do what they gotta do. Mail, DNS etc. Limited to 1Mbps.
Now I set up a class-map for each protocol I was interested in. The Cisco 877 has some protocol information builtin such as for Skype:
class-map match-any skype match protocol skype
Others can be defined manually with access lists.
ip access-list extended steam permit tcp any range 27014 27050 any class-map match-any steam match access-group name steam
Further class maps allow grouping of protocols according to the classification defined earlier. Here’s medium. lowest, low and high are similar. These are match-any classes which match any of the listed protocols.
class-map match-any medium match class-map http match class-map skype
A final set of class maps match only at peak time. These are match-all classes so both criteria – it’s peak time and it’s a particular protocol class – must match. Here’s peak-medium.
class-map match-all peak-medium match access-group name peak match class-map medium
One more class, peak-default acts as the catchall.
class-map match-all peak-default match access-group name peak match not class-map lowest match not class-map low match not class-map medium match not class-map high
With those classes defined we can now set up a policy-map which assigns a DSCP tag to traffic matching particular classes.
policy-map peak class peak-default set dscp 1 class peak-lowest set dscp 2 class peak-low set dscp 3 class peak-medium set dscp 4 class peak-high set dscp 5
To convert these policies into actual rate limiting we set rate-limit rules matching the defined DSCP values on the ADSL interface, which for me is Dialer0.
rate-limit expects three numbers: a target bitrate, a normal burst rate and a maximum burst rate. Cisco recommend setting the normal parameter as 1.5/8 x the target and the maximum as twice the normal. So for the 128kbps profile (DSCP 3) the numbers are 128000 24000 48000. If in doubt just multiply the target rate by 0.1875 for the second number and then double it…
interface Dialer0 rate-limit input dscp 1 64000 12000 24000 conform-action transmit exceed-action drop rate-limit input dscp 2 32000 6000 12000 conform-action transmit exceed-action drop rate-limit input dscp 3 128000 24000 48000 conform-action transmit exceed-action drop rate-limit input dscp 4 256000 48000 96000 conform-action transmit exceed-action drop rate-limit input dscp 5 1024000 192000 384000 conform-action transmit exceed-action drop
Actually there is one more thing. As it stands the configuration won’t have any effect. We have to apply the service policy to the interface for the magic to happen.
interface Dialer0 service-policy input peak
Initial testing suggests that this works. A Steam download at peak time claims to run at 7kBps and at 800kBps at off-peak. Temporarily adding a line to the peak time range allows easy testing when the actual time is off-peak.
I’m sure I’ll need to tweak the download rates and/or move protocol definitions around as real life usage patterns become apparent but the underlying concepts work well enough.