QoS: Skype

Hello network admins,
Everyone knows our PITA Skype protocol, and its peer to peer obfuscated connections.
To identify the traffic, usually I used the L7 patterns found on protocol.info.
While sometimes it worked pretty fine, I noticed a lot of overmatch (mostly P2P downloads)
After an hardware failure (damn CF cards) i had to reconfigure a QoS, i thought a better way to identify Skype traffic..
I searched some info about Skype protocol and found this interesting presentation on blackhat.com site where the author hijacked the Skype network. At page 75, I found a interesting pattern of Skype connections which can be used to identify Skype traffic.

The very first UDP packet received by a Skype client will be a NAck
This packet is not crypted
This packet is used to set up the obfuscation layer
Skype can’t communicate on UDP without receiving this one



NAck packet: how does Skype know the public IP
1 At the begining, it uses 0.0.0.0
2 Its peer won’t be able to decrypt the message (bad CRC)
3 =) The peer sends a NAck with the public IP
4 Skype updates what it knows about its public IP accordingly

We can use this NAck packet to identify the peers, and mark the connections to that peer (at max 50kbps)..

Identify the NAck packet
We know that the NAck packet size is 39 bytes and there should be our public IP from the 4th byte of the payload.
We need a customized L7 filter to match the 4th byte.
IE: my public IPs are 92.x.x.x and 213.x.x.x so my matching regex will be:

[\\|\xd5]
[\\ = 92
| = or 
\xd5] = 213

where \ is 92 and \xd5 is 213 (you can calcolate your hex resolution here)
Here’s the ROS Rules:

/ip firewall layer7-protocol add name=skypenack regexp="[\\\\|\\xd5]"
/ip firewall mangle add action=add-src-to-address-list address-list=skype address-list-timeout=1h chain=forward disabled=no layer7-protocol=skypenack packet-size=39 protocol=udp

TODO: Refine the L7 pattern to avoid overmatch

Marking the Traffic
Mark the traffic from/to the fresh address list that don’t exceed the 50kbit bandwidth usage (to not include the skype file transfers)

 /ip firewall mangle add action=mark-connection chain=forward connection-rate=0-50k disabled=no new-connection-mark=conn_skype passthrough=yes protocol=udp src-address-list=skype
/ip firewall mangle add action=mark-connection chain=forward connection-rate=0-50k disabled=no dst-address-list=skype new-connection-mark=conn_skype passthrough=yes protocol=udp
/ip firewall mangle add action=mark-packet chain=forward connection-mark=conn_skype disabled=no new-packet-mark=skype passthrough=no

Try this out and give feedbacks and suggestions

How to change that rule if I have only one public ip: 213.x.x.x.
For what version of routeros it is suited?

This works with all the version post 3.20 i think… Tested on 4.11 and 5.0RC1

/ip firewall layer7-protocol add name=skypenack regexp="\\xd5"

Thanks ti seems it works fine. Matching only skype communication. I test it on main router. I will give you now, if any problem.
I still dont understant that l7 rule:
213 is d5, you put there \xd5 (why also \x)
92 is 5c

my ip is x.y.z.q, you use just x in that rule or also something else?

Thank you for your Feedback!
“\xd5”: the backslashes are doubled because one is an escape for the code.. if you insert them by winbox GUI, you don’t need it, while you need it by CLI.
92 is 5c but ROS checks ASCI codes before HEX, so “\” means “\x5c” (Don’t ask me the reasons of this behaviour :laughing: ) If you insert \x5c, ROS will return you an error..

I’m using only x. Maybe you can refine it with y and z, but the improvement will be minimal

Very interesting topic.

Some questions/remarks though:

  1. What if several Skype users are behind one NAT firewall? Is Skype not using more info on the subscriber (like src port-IP combination) so several Skype comms can run at the same time from one IP?
    But I presume that that is not so important to us. We need to filter Skype then before we apply the natting on it? What is your suggestion? In a mixed network with even some old rb112’s around should we do this at the client CPE and then give that traffic a TOS marker over the rest of the network?
    Or should we do it in the prerouting chain on the local port of the border router (=more powerfull)?

  2. Skype made its protocol hard to catch not to have it easy blocked by ISP’s. If we now found an relative easy way of identifying its traffic we can off course prioritize it to grant it a better quality but at the same time it can be used to block it as well… How long would it take for Skype to modify their initial ´handshaking´ so your solution won’t work any longer?

  3. Is this first package always the same for all Skype versions. So, does it work on all Skype versions? And how easy can they change the package to avoid us finding it?

  4. Maybe we, (W)ISP’s that actually want to help Skype traffic to highest QoS leves should ask Skype developers to embed a sort of ´disguise/recognize´ button on each skype. If they would have a special package embedded in their default Skype program that makes the whole data stream very simple recognizable the ISP’s (and router manufacturer’s) can easy filter it and prioritize it.
    Then, if user thinks he is denied or shaped his Skype connection he could go into ´obscured´ mode so blocking would become very hard…
    I know, this is something Skype developers have to do but it needs a gentle kick under their *ss to get it done…

A lot of questions! :laughing:

  1. I suggest to use this on your border router, since is quite cpu intensive (for a RB112, a RB411 might handle this without problems).
    The NACK packet has the pubblic address not natted so you need to specify the public IPs that usually your ISP gives you (a business connection has either a static IP or a small range of public IPs) in the L7 pattern.
  2. I don’t know if Skype will change its Acknowledge methods soon, since it has to preserve legacy connections between old skype versions and newer ones.
    3 Yes, it looks like the package is always the same.
    4 The Disguise/Recognize button is a great idea imho :wink:

I am afraid I don’t fully understand this..
My CPE is on a local IP. Meaning all traffic leaving from this CPE has an IP address from its WAN facing interface.
Only in the border router the IP gets translated into the public IP.

Should I not use the CPE-WAN address in your “regexp=”\xd5" " code? (The xd5 has to be representing my real IP class A notificaton)
If I use this filter now on my CPE and give the packets a TOS value which then can be used by all routers for priority this TOS value stays the same even in the case the IP in the packet header is changed by the srce-NAT rule in my border router?

OR, should I better filter Skype on packets already having the public IP address assigned? (So on a router ´outside´ my border router. I have a transparant router doing QoS on packets already src.natted by main gateway router of my network.
Now the code can represent the public IP and since we make connection markers anyway the conn. tracker takes care both directions of Skype traffic will get priority by designed rules and this priority then persists on the Skype package even on my local network?
Advantage in this setup would be that now a more powerfull router takes care of the L7 filter.
Disadvantage will be the the first initial traffic generated by the Skype software from the client cannot be filtered on its firt voyage from the CPE to the border router. (Since only after that border router my transparant QoS router will filter it.)

What do you think of this?

The NACK Packet always returns with the Public IP (Necessary for Skype peering) so your regex (even in a natted CPE) must contain your class A Public address range.
I saw a very low impact on performance, so i think you can use your idea of TOS from the CPE.
The NACK Packet anyway doesn’t exchange any valuable data beside the Public IP so it’s not involved on skype calls or chats. Another connection will be established for that. But you already recognized the Source/Destination IPs :wink:
I don’t know much about your network infrastructure, so i cannot recommend you the best way to QoS it.

Can I block skype, if I drop “skype” address list, skype still working?

I didn’t try to block Skype. Just try it. It should connect but if you drop connections, it shouldn’t exchange any data..

I drop “skype” address list, but I still can talk and call, everything works. In drop rule packets count grow, so drop work fine… :frowning:

Post your dropping rules..

/ip firewall layer7-protocol print

NAME REGEXP

0 skypenack [\x4a.\x3a.\xda.\xca]

/ip firewall mangle print
2 X chain=forward action=add-src-to-address-list protocol=udp
address-list=skype address-list-timeout=1h layer7-protocol=skypenack
packet-size=39

/ip firewall filter print (first forward rule)
27 ;;; Skype
chain=forward action=drop dst-address-list=skype

drop src-address-list too

I’m already tried drop:
src
dst
src and dst
Whether someone was able to block skype?

By public IP you mean the IP assigned by the ISP to the NAT router that connects the rest of the network to the internet?
What about a NAT router that has several 10ths of users all using Skype but they all get out to the internet with the same public IP. How does Skype now know to which traffic belongs?
In such case that many users are behind NAT firewall and Skype would only work with public nat than Skype also needs to know the port numbers. Otherwise it cannot distinguis between different users.

Or, the public IP of the Nack packet must be set by nat router and in the return is set back to users local IP?

In the Opening Post, i linked a pdf of a guy that analyzed skype protocol..
Look there if you find something useful.
This thread is not meant for blocking skype, but only to recognize it.

I think you are overseeing the whole NACK packet story..
There’s no way to identify skype connections or packets, the only packet that does keep the same pattern is the NACK Packet.
Once we get the source address of that NACK packet, we can identify the skype peers and then mark the connection between the peer and your CPE. No matter where you filter that packet, even after 3 nats, it will always contain the public ip of your network.

I am struggling to get this to work but so far no luck. All that I can make to happen is that when logging into Skype the first time a series of ´foreign´ IP’s are listed in my “skype” address list.
When Skype is just standby sometimes I see a new IP beeing add.
But thats it. The next mangle rules that are looking for these IP’s either as dst-address or src-address and with given speed with udp protocol are not counting anything.

So I still have some questions:

  • This “NACK” package, is that generated when client logs in for the first time and the Skype program contacts Skype nodes or supernodes?
  • Or is this “Nack” package also generated each time a connection is build to make a communication session?
  • I already learned that Skype-to-Skype is something different than “Skype-to-PSTN”. Would this make any difference for the discussd methode?
  • Skype communication with camera? How do we filter this traffic. Is the video stream completely separated from the voice data stream? I also learned that Skype adapts needed bandwith for the video stream to the available bandwith. It can use up to 1Mb up and download if given! But even with 300kbps a lesser video conversation is possible.

The IP’s the filter is catching and putting them in the “skype” address list; what are these IP’s? Are they nodes / supernodes, or are they IP’s of clients skype shows are ´online´?
Why do we give these IP¡s a timeout of 1 hour anyway? I understand nodes and supernodes can move but I would say “not every hour”! And even so, if they move, Skype client program has to find the new nodes and will therefore send new “nack” package? (Which we will find..)

Hi Medianet.

I need some convincing!

I have tried out your suggestions, however I could not get any matches by using the first octet of my ISP’s IP in the layer 7 match.

My PC is routed up to the point of my gateway, at which point I am natted (but only the once)


However, on some clients CPE’s I have tried the same rules, but by changing the match to the local networks first octet. Lets say for example that my cpe’s wlan 1st octet is 187, it so happens on my network that the cpe ethernet interface also has the same 1st octet 187.

Under those circumstances, there are some matches, but I suspect that these are random entries and that it would be chaos if it wasn’t for the fact that the following mangle rules have refined the connections by using “connection rate” matchers…

(incidentally I refined those to 15k-45k!) and finalised the whole routine by applying dscp46 which is then used for shaping and qos in the gateway (pcq)

All said, it seems to work fine, but I suspect that it is by more of the influence of the connection rate traps rather than by the layer 7 match.

I tried wireshark, but I could see no evidence of what has been suggested.

Have you proved it by using “wireshark” or “ethereal” and if so, what filters did you use to prove the case.