In this document, we will cover how to accomplish the above goal using a D-Link DI-614+ router, and mIRC 6.1.
If you're using different equipment, fear not, as the concept itself is what makes all the difference. Regardless, what you're going to need is following:
It is important that you have a NAT unit that permits static port forwarding. The term "static" is used to describe port forwards (from WAN to LAN) that are not conditional ("triggered"), and do not time out. Using dynamic port forwarding ("triggers") will work, however all routers contain an expiry for such port forwards. So, in the case that you connect to an IRC network and don't attempt an outgoing DCC within the expiry time used by the router, the port forward will essentially become inapplicable until you reconnect to the IRC network. This is one of the core problems with using "triggered" port forwards.
You will also need an IRC client that allows you to configure a port range for outgoing DCCs. There are a lot of great IRC clients out there for different operating systems, but not all of them permit you to do this. If your client does not support this, I recommend you get one which does, or contact your clients' author and demand the feature (it requires very little effort on the author's part, as specifying such is part of the standard libc socket library!). By default, IRC clients will attempt to send outgoing DCCs on a dynamically allocated port number, which simply will not work with NAT (since IRC does not use UPnP).
NOTE: This only applies to outgoing IRC DCC requests. Incoming DCCs should work just fine using NAT (assuming your NAT router has a proper NAT implementation). If incoming DCCs do not work, your problem is elsewhere.
The problem with outgoing IRC DCCs -- like most P2P (peer-to-peer) applications -- is that the port numbers are transmitted to the remote end as part of a data packet and not "negotiated" like UPnP provides. IRC DCC was invented long before UPnP, and will probably never be upgraded to support this kind-of feature.
Outgoing IRC DCCs include DCC SENDs, DCC RESUMEs, and DCC CHATs.
Let's take the following scenario and map out exactly what is happening on a network level, so that you can understand exactly where the problem with outgoing IRC DCC lies. In this example, we will be doing a DCC SEND (a file send), and will assume the following information:
192.168.0.0/24 = Local network (LAN) 192.168.0.1 = NAT gateway (on LAN) 184.108.40.206 = NAT WAN-side IP ("Internet IP") 220.127.116.11 = irc.dal.net (IRC server) SenderNick = Nickname of individual doing DCC SEND (us) ReceiverNick = Nickname of individual receiving file 18.104.22.168 = IP of ReceiverNick
|#||Source IP||Source Port||Destination IP||Destination Port||Packet data / Description|
|2||192.168.0.10||n/a||192.168.0.1||n/a||The PRIVMSG (DCC SEND) goes through the NAT gateway.|
|3||192.168.0.10||1027||n/a||n/a||192.168.0.10 (the LAN IP of SenderNick's PC) begins listening on port 1027 for the incoming DCC connection so it can send the file.|
|5||22.214.171.124||3097||192.168.0.10||1027||126.96.36.199 (ReceiverNick) receives the DCC SEND request from irc.dal.net, and therefore attempts to connect to 192.168.0.10 on port 1027.|
NOTE: The IP shown in
DCC SEND test.txt 192.168.0.10 1027
is not actually a user-readable/plain-text IP number. It is actually the
32-bit Internet-packed representation of the IP number. I used the unpacked
version so it would make more sense to readers.
You can see exactly why this doesn't work. The problem is that the actual IP of the sender is contained in the packet which the recipient attempts to connect to. 188.8.131.52 will never be able to connect to 192.168.0.10; it's not on the same network.
Thankfully, port forwarding can solve this problem (as can it with most other P2P protocols! This isn't just limited to IRC, you know...)
The trick involves three (3) changes:
Something that needs to be made clear here: this solution will not work with DHCP. DHCP, by it's nature, is a dynamic protocol -- and although you may get assigned the same IP for many months, there is no way to guarantee you will get it every time. If you use DHCP, either stop using it and assign your LAN PCs static IPs, or simply rely on other methods of file transfer or IM clients (such as MSN Messenger 6.0, which supports UPnP).
NOTE: D-Link D-614+ firmwares 3.20 (for Revision B models) and 2.20 (for Revision A models) exhibit known bugs in regards to port forwarding (the "Virtual Server," "Application," and "Firewall" settings). The end result is that any incoming connections to ports -- forwarded or not -- will fail and spit back TCP RST ("Connection refused"). D-Link has not acknowledged this problem, but it has been reported by numerous members of the D-Link forum over at BroadbandReports. There are other known problems with the 3.20/2.20 firmwares as well, including spontaneous reboots.
NOTE: This step is dependant upon what NAT router/gateway you own. The examples shown here are for a D-Link DI-614+. Please refer to your users manual for assistance, or call Technical Support.
[*] Enabled [ ] Disabled Name IRC file sends (PC#1) Action [*] Allow [ ] Deny Interface IP Range Start IP Range End Protocol Port Range Source WAN * Destination LAN 192.168.0.10 TCP 54000-54019 Schedule [*] Always
If you suspect the IP address in the PRIVMSG (DCC SEND) packet is wrong, try sending something to a friend. mIRC will conveniently send a NOTICE message along with any DCC SENDs, which means your friend should see something that resembles the following:
-SenderNick- DCC Send test.txt (184.108.40.206)
Make sure the IP shown (e.g. 220.127.116.11) matches your WAN-side IP address. You can verify this by doing a /WHOIS on yourself and doing a /DNS on the hostname you show up on IRC from, or just by doing a /DNS on your own nickname (i.e. /DNS SenderNick).
If the IP address shown in the NOTICE is your LAN-side IP address, you either did not reconnect to the IRC network, or mIRC is not set to do a "Server" hostname/IP lookup. Double-check your settings.
If you have multiple PCs on the same LAN that need to do IRC DCCs (such as if you live in a household full of geeks who all use IRC), apply the following concepts to the above solution: