sbstp / rust-igd

Internet Gateway Device (UPNP) client
https://docs.rs/igd/
MIT License
105 stars 41 forks source link

IGD 2.0 support #12

Open vinipsmaker opened 8 years ago

canndrew commented 8 years ago

Ever since the add_any_port method was added this library has had some support for IGD 2.0 although it by no means supports all the IGD 2.0 methods (or all the IGD 1.0 methods for that matter).

marco-c commented 7 years ago

A first step would be to search for IGDv2 devices too (and then use the v1 methods). This would be useful if there are IGDv2 devices that respond to a IGDv2 search and not a IGDv1 one.

povilasb commented 6 years ago

@marco-c I think I've got such device. What's interesting is that it's SSDP response is:

HTTP/1.1 200 OK
CACHE-CONTROL: max-age=120
DATE: Fri, 12 Jan 2018 12:15:39 GMT
ST: urn:schemas-upnp-org:device:InternetGatewayDevice:1
USN: uuid:05e61700-3323-4862-a3d7-ba2144542e75::urn:schemas-upnp-org:device:InternetGatewayDevice:1
EXT:
SERVER: OpenWRT/OpenWrt/Attitude_Adjustment__r43446_ UPnP/1.1 MiniUPnPd/1.8
LOCATION: http://192.168.1.254:5000/rootDesc.xm

which clearly states that version is actualy 1

urn:schemas-upnp-org:device:InternetGatewayDevice:1

But then $ curl http://192.168.1.254:5000/rootDesc.xml returns

<?xml version="1.0"?>
<root xmlns="urn:schemas-upnp-org:device-1-0">
    <specVersion>
        <major>1</major>
        <minor>0</minor>
    </specVersion>
    <device>
        <deviceType>urn:schemas-upnp-org:device:InternetGatewayDevice:2</deviceType>
        <friendlyName>MediaAccess TG389ac (1643RA65K)</friendlyName>
        <manufacturer>Technicolor</manufacturer>
        <manufacturerURL>http://www.technicolor.com/</manufacturerURL>
        <modelDescription>Technicolor Internet Gateway Device</modelDescription>
        <modelName>MediaAccess TG</modelName>
        <modelNumber>389ac</modelNumber>
        <modelURL>http://www.technicolor.com/</modelURL>
        <serialNumber>1643RA65K</serialNumber>
        <UDN>uuid:05e61700-3323-4862-a3d7-ba2144542e75</UDN>
        <serviceList>
            <service>
                <serviceType>urn:schemas-upnp-org:service:Layer3Forwarding:1</serviceType>
                <serviceId>urn:upnp-org:serviceId:Layer3Forwarding1</serviceId>
                <controlURL>/aGRJQiI/ctl/L3F</controlURL>
                <eventSubURL>/aGRJQiI/evt/L3F</eventSubURL>
                <SCPDURL>/aGRJQiI/L3F.xml</SCPDURL>
            </service>
        </serviceList>
        <deviceList>
            <device>
                <deviceType>urn:schemas-upnp-org:device:WANDevice:2</deviceType>
                <friendlyName>WANDevice</friendlyName>
                <manufacturer>MiniUPnP</manufacturer>
                <manufacturerURL>http://miniupnp.free.fr/</manufacturerURL>
                <modelDescription>WAN Device</modelDescription>
                <modelName>WAN Device</modelName>
                <modelNumber>20160726</modelNumber>
                <modelURL>http://miniupnp.free.fr/</modelURL>
                <serialNumber>1643RA65K</serialNumber>
                <UDN>uuid:05e61700-3323-4862-a3d8-ba2144542e75</UDN>
                <UPC>000000000000</UPC>
                <serviceList>
                    <service>
                        <serviceType>urn:schemas-upnp-org:service:WANCommonInterfaceConfig:1</serviceType>
                        <serviceId>urn:upnp-org:serviceId:WANCommonIFC1</serviceId>
                        <controlURL>/aGRJQiI/ctl/CmnIfCfg</controlURL>
                        <eventSubURL>/aGRJQiI/evt/CmnIfCfg</eventSubURL>
                        <SCPDURL>/aGRJQiI/WANCfg.xml</SCPDURL>
                    </service>
                </serviceList>
                <deviceList>
                    <device>
                        <deviceType>urn:schemas-upnp-org:device:WANConnectionDevice:2</deviceType>
                        <friendlyName>WANConnectionDevice</friendlyName>
                        <manufacturer>MiniUPnP</manufacturer>
                        <manufacturerURL>http://miniupnp.free.fr/</manufacturerURL>
                        <modelDescription>MiniUPnP daemon</modelDescription>
                        <modelName>MiniUPnPd</modelName>
                        <modelNumber>20160726</modelNumber>
                        <modelURL>http://miniupnp.free.fr/</modelURL>
                        <serialNumber>1643RA65K</serialNumber>
                        <UDN>uuid:05e61700-3323-4862-a3d9-ba2144542e75</UDN>
                        <UPC>000000000000</UPC>
                        <serviceList>
                            <service>
                                <serviceType>urn:schemas-upnp-org:service:WANIPConnection:2</serviceType>
                                <serviceId>urn:upnp-org:serviceId:WANIPConn1</serviceId>
                                <controlURL>/aGRJQiI/ctl/IPConn</controlURL>
                                <eventSubURL>/aGRJQiI/evt/IPConn</eventSubURL>
                                <SCPDURL>/aGRJQiI/WANIPCn.xml</SCPDURL>
                            </service>
                        </serviceList>
                    </device>
                </deviceList>
            </device>
        </deviceList>
        <presentationURL>http://192.168.1.254/</presentationURL>
    </device>
</root>

Where you can find

urn:schemas-upnp-org:service:WANIPConnection:2

And because of this rust-igd fails to find IGD device on LAN. But such a simple patch fixes discovery and the rest works smoothly:

--- a/src/search.rs
+++ b/src/search.rs
@@ -215,6 +215,7 @@ fn get_control_url(location: &(SocketAddrV4, String)) -> Result<String, SearchEr
                         .zip(tail)
                         .all(|(l, r)| l == r) {
                     if ("urn:schemas-upnp-org:service:WANIPConnection:1" == service.service_type ||
+                        "urn:schemas-upnp-org:service:WANIPConnection:2" == service.service_type ||
                         "urn:schemas-upnp-org:service:WANPPPConnection:1" == service.service_type) &&
                         service.control_url.len() != 0 {
                         return Ok(service.control_url)
marco-c commented 6 years ago

Since IGDv2 is backwards compatible, I think your patch should be safe. urn:schemas-upnp-org:service:WANPPPConnection:2 should probably be added too.