DLNA协议分析

本文在iPhone 用抓包的方式来分析DLNA协议

一.抓包准备工作

我们是在MacBook 上用iPhone内置 RVI (虚拟网卡)来进行抓包.

iOS 5后,apple引入了RVI remote virtual interface的特性,它只需要将iOS设备使用USB数据线连接到mac上,然后使用rvictl工具以iOS设备的UDID为参数在Mac中建立一个虚拟网络接口rvi,就可以在mac设备上使用tcpdump,wireshark等工具对创建的接口进行抓包分析了。

这个机制相对于 Charles搭代理服务器抓包这个办法而言,不仅硬件环境简单,就是xcode真机开发环境本身,而且能抓wifi和移动数据包所有数据.相当方便.

步骤:
第一步:使用USB数据线将iOS设备连接到MAC上

第二步:获得iOS设备的UDID,可以使用iTunes查看,也可以使用Xcode的Organizer工具查看

第三步:创建RVI接口
在mac 终端执行命令
$ rvictl -s <UDID>
这样会创建一个虚拟网卡rv0

用ifconfig rv0 可以看数据

rvictl -s 270516bef723f891416e46270b4026d3e8b1f172

Starting device 270516bef723f891416e46270b4026d3e8b1f172 [SUCCEEDED] with interface rvi0

bluedrum:~ pro$ ifconfig rvi0
rvi0: flags=3005<UP,DEBUG,LINK0,LINK1> mtu 0

第四步: 用抓包软件针对rv0抓包即可.
这里我使用 wireshark,在新建时,选rvi0进行抓包

image.png

正在抓包界面

image.png

第五步:分析结束后,移除创建的RVI接口
$ rvictl -x <UDID>

二.DLNA 协议

数字生活网络联盟 Digital Living Network Alliance (DLNA)

DLNA采用upnp 协议格式. 主要分为两大块,一个是发现控制器 SSDP,它通过udp 来实现

二是控制协议 SOAP ,即开始投屏后发投屏设备发送 前进,后退,暂停,调节音量等操作.

DLNA各种设备术语:

  1. Digital Media Controller(DMC)数位媒体控制器: 作为遥控装置使用,可寻找DMS上的多媒体档案,并指定可播放该多媒体档案的DMR进行播放或是控制多媒体档案上下传到DMS的装置,一般是手机.

  2. Digital Media Server(DMS)数位媒体服务器: 提供了媒体档案的获取、录制、储存以及作为源头的装置。一般是公网上流媒体服务器

  3. Digital Media Renderer(DMR)数位媒体控制器: 可接收并播放从DMC push过来的媒体档案。即接收投屏数据,一般是智能电视, OTT盒子等.

这三者的关系是,DMC通过获取DMS上的歌曲或者视频(也可以不是DMS上的,而仅仅只是一个链接),把它们传送到DMR上,由DMR进行播放。

三.DLNA 发现控制协议

即DMC 通过upnp广播 发现局域网中DMR设备.

这里我们抓iOS 咪咕视频的发现为分析例子.

image.png

步骤是, DMC 首先向固定的 多播地址(239.255.255.250:1900)发送UDP广播包. DMR收到数据后,会用UDP响应数据

3.1 M-SEARCH 包格式

实际包格式


image.png

http包头格式:

  • M-SEARCH * HTTP/1.1 起始行,表明是一个SSDP搜索消息
  • HOST 多播地址和端口
  • MAN 协议查询类型,必须是ssdp:discover
  • MX 设备响应最长等待时间;设备在0和这个值之间随机选择一个时间最为延迟,避免多个设备同时响应造成网络拥堵
    +ST 搜索的目标,通常为upnp:rootdevice (值域为 ssdp:all、upnp:rootdevice、uuid:device-UUID、urn:schemas-upnp-org:devices:device-Type:version、urn:schemas-upnp-org:service:service-Type )
  • User-Agent DMC设备名称
M-SEARCH * HTTP/1.1
MX: 5
ST: upnp:rootdevice
MAN: "ssdp:discover"
User-Agent: UPnP/1.0 DLNADOC/1.50 Platinum/1.0.5.13
Connection: close
Host: 239.255.255.250:1900


3.1 响应包格式

image.png
  • HTTP/1.1 200 OK 起始行,表明是一个HTTP响应消息
  • CACHE_CONTROL 消息存活时间
  • DATE 响应生成的时间
  • EXT N/A
  • LOCATION 设备描述的URL
  • SERVER 包含设备上的操作系统名、版本、产品名称和产品版本信息
  • ST 与搜索消息相同
    USN 唯一服务名称,SSDP使用通用唯一标识符UUID作为某个设备/服务的全球唯一标识
HTTP/1.1 200 OK
LOCATION: http://169.254.100.156:37215/upnpdev.xml
SERVER: Linux UPnP/1.0 Huawei-ATP-IGD
CACHE-CONTROL: max-age=86500
EXT: 
ST: upnp:rootdevice
USN: uuid:00e0fc37-2525-2828-2500-0034fe66fdc6::upnp:rootdevice
DATE: Fri, 20 Jul 2018 07:11:30 GMT


LOCATION: http://192.168.0.108:49152/description.xml
还有一种格式采用NOTIFY,主动向广播发送自己信息,这是小米电视主动发送通知

image.png
NOTIFY * HTTP/1.1
HOST: 239.255.255.250:1900
CACHE-CONTROL: max-age=62
LOCATION: http://192.168.0.108:49152/description.xml
NT: urn:schemas-upnp-org:service:AVTransport:1
NTS: ssdp:alive
SERVER: Linux/3.14.29, UPnP/1.0, Portable SDK for UPnP devices/1.6.13
USN: uuid:F7CA5454-3F48-4390-8009-4c3848e24612::urn:schemas-upnp-org:service:AVTransport:1

其中LOCATION 是一个指向xml 下载网址,里面描述设备真正的信息

以下是一个小米音箱的响应

<?xml version="1.0" encoding="utf-8"?>
<root
    xmlns="urn:schemas-upnp-org:device-1-0">
    <specVersion>
        <major>1</major>
        <minor>1</minor>
    </specVersion>
    <device>
        <deviceType>urn:schemas-upnp-org:device:MediaRenderer:1</deviceType>
        <friendlyName>灏忕背AI闊崇-8003</friendlyName>
        <manufacturer>Mi, Inc.</manufacturer>
        <modelDescription>The Mi AI SoundBox</modelDescription>
        <modelName>S12</modelName>
        <modelNumber>S12</modelNumber>
        <qq:X_QPlay_SoftwareCapability
            xmlns:qq="http://www.tencent.com">QPlay:2
        </qq:X_QPlay_SoftwareCapability>
        <dlna:X_DLNADOC
            xmlns:dlna="urn:schemas-dlna-org:device-1-0">DMR-1.50
        </dlna:X_DLNADOC>
        <dlna:X_DLNACAP
            xmlns:dlna="urn:schemas-dlna-org:device-1-0">,
        </dlna:X_DLNACAP>
        <UDN>uuid:d3b1a06a-8fb6-4f5b-b042-a15d1b956fb8</UDN>
        <serviceList>
            <service>
                <serviceType>urn:schemas-upnp-org:service:AVTransport:1</serviceType>
                <serviceId>urn:upnp-org:serviceId:AVTransport</serviceId>
                <SCPDURL>AVTransport1.xml</SCPDURL>
                <controlURL>/AVTransport/control</controlURL>
                <eventSubURL>/AVTransport/event</eventSubURL>
            </service>
            <service>
                <serviceType>urn:schemas-upnp-org:service:ConnectionManager:1</serviceType>
                <serviceId>urn:upnp-org:serviceId:ConnectionManager</serviceId>
                <SCPDURL>ConnectionManager1.xml</SCPDURL>
                <controlURL>/ConnectionManager/control</controlURL>
                <eventSubURL>/ConnectionManager/event</eventSubURL>
            </service>
            <service>
                <serviceType>urn:schemas-upnp-org:service:RenderingControl:1</serviceType>
                <serviceId>urn:upnp-org:serviceId:RenderingControl</serviceId>
                <SCPDURL>RenderingControl1.xml</SCPDURL>
                <controlURL>/RenderingControl/control</controlURL>
                <eventSubURL>/RenderingControl/event</eventSubURL>
            </service>
            <service>
                <serviceType>urn:xiaomi-com:service:Queue:1</serviceType>
                <serviceId>urn:xiaomi-com:serviceId:Queue</serviceId>
                <SCPDURL>Queue1.xml</SCPDURL>
                <controlURL>Queue1/control</controlURL>
                <eventSubURL>Queue1/event</eventSubURL>
            </service>
            <service>
                <serviceType>urn:xiaomi-com:service:Playlist:1</serviceType>
                <serviceId>urn:xiaomi-com:serviceId:Playlist</serviceId>
                <SCPDURL>Playlist1.xml</SCPDURL>
                <controlURL>Playlist1/control</controlURL>
                <eventSubURL>Playlist1/event</eventSubURL>
            </service>
            <service>
                <serviceType>urn:schemas-tencent-com:service:QPlay:1</serviceType>
                <serviceId>urn:tencent-com:serviceId:QPlay</serviceId>
                <SCPDURL>QPlay1.xml</SCPDURL>
                <controlURL>QPlay1/control</controlURL>
                <eventSubURL>QPlay1/event</eventSubURL>
            </service>
            <service>
                <serviceType>urn:xiaomi-com:service:Favorites:1</serviceType>
                <serviceId>urn:xiaomi-com:serviceId:Favorites</serviceId>
                <SCPDURL>Favorites1.xml</SCPDURL>
                <controlURL>Favorites1/control</controlURL>
                <eventSubURL>Favorites1/event</eventSubURL>
            </service>
        </serviceList>
    </device>
</root>

其中friendlyName 是比较友好的显示名字,一般显示在设备上.
modelName 是英文名字

天猫盒子的设备描述

<root xmlns="urn:schemas-upnp-org:device-1-0">
<specVersion>
<major>1</major>
<minor>0</minor>
</specVersion>
<device>
<deviceType>urn:schemas-upnp-org:device:MediaRenderer:1</deviceType>
<UDN>uuid:595d5f67-dc56-3ac7-118b-2fab9893c7b7</UDN>
<friendlyName/>
<manufacturer>www.yunos.com</manufacturer>
<manufacturerURL>www.yunos.com</manufacturerURL>
<modelDescription>YunOS UPnP/DNLA DMR</modelDescription>
<modelName>MagicBox_M17</modelName>
<modelNumber>3.0.4-gp3.0.4</modelNumber>
<modelURL>www.yunos.com</modelURL>
<yingshiVersion>2120513812</yingshiVersion>
<rcsPort>13510</rcsPort>
<serviceList>
<service>
<serviceType>urn:schemas-upnp-org:service:AVTransport:1</serviceType>
<serviceId>urn:upnp-org:serviceId:AVTransport</serviceId>
<controlURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/AVTransport/action
</controlURL>
<eventSubURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/AVTransport/event
</eventSubURL>
<SCPDURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/AVTransport/desc.xml
</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:RenderingControl:1</serviceType>
<serviceId>urn:upnp-org:serviceId:RenderingControl</serviceId>
<controlURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/RenderingControl/action
</controlURL>
<eventSubURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/RenderingControl/event
</eventSubURL>
<SCPDURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/RenderingControl/desc.xml
</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:ConnectionManager:1</serviceType>
<serviceId>urn:upnp-org:serviceId:ConnectionManager</serviceId>
<controlURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/ConnectionManager/action
</controlURL>
<eventSubURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/ConnectionManager/event
</eventSubURL>
<SCPDURL>
/dev/595d5f67-dc56-3ac7-118b-2fab9893c7b7/svc/upnp-org/ConnectionManager/desc.xml
</SCPDURL>
</service>
</serviceList>
</device>
</root>

小米电视的通知

<specVersion>
<major>1</major>
<minor>0</minor>
</specVersion>
<device>
<deviceType>urn:schemas-upnp-org:device:MediaRenderer:1</deviceType>
<presentationURL>/</presentationURL>
<friendlyName>客厅的小米电视</friendlyName>
<manufacturer>Xiaomi</manufacturer>
<manufacturerURL>http://www.xiaomi.com/</manufacturerURL>
<modelDescription>Xiaomi MediaRenderer</modelDescription>
<modelName>Xiaomi MediaRenderer</modelName>
<modelURL>http://www.xiaomi.com/hezi</modelURL>
<UPC>000000000017</UPC>
<UDN>uuid:F7CA5454-3F48-4390-8009-4c3848e24612</UDN>
<UID>-982164636</UID>
<serviceList>
<service>
<serviceType>urn:schemas-upnp-org:service:AVTransport:1</serviceType>
<serviceId>urn:upnp-org:serviceId:AVTransport</serviceId>
<SCPDURL>/dlna/Render/AVTransport_scpd.xml</SCPDURL>
<controlURL>_urn:schemas-upnp-org:service:AVTransport_control</controlURL>
<eventSubURL>_urn:schemas-upnp-org:service:AVTransport_event</eventSubURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:ConnectionManager:1</serviceType>
<serviceId>urn:upnp-org:serviceId:ConnectionManager</serviceId>
<SCPDURL>/dlna/Render/ConnectionManager_scpd.xml</SCPDURL>
<controlURL>
_urn:schemas-upnp-org:service:ConnectionManager_control
</controlURL>
<eventSubURL>
_urn:schemas-upnp-org:service:ConnectionManager_event
</eventSubURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:RenderingControl:1</serviceType>
<serviceId>urn:upnp-org:serviceId:RenderingControl</serviceId>
<SCPDURL>/dlna/Render/RenderingControl_scpd.xml</SCPDURL>
<controlURL>
_urn:schemas-upnp-org:service:RenderingControl_control
</controlURL>
<eventSubURL>
_urn:schemas-upnp-org:service:RenderingControl_event
</eventSubURL>
</service>
<service>
<serviceType>urn:mi-com:service:RController:1</serviceType>
<serviceId>urn:upnp-org:serviceId:RController</serviceId>
<SCPDURL>/dlna/Render/RControl_scpd.xml</SCPDURL>
<controlURL>
_urn:schemas-upnp-org:service:RenderingControl_control
</controlURL>
<eventSubURL>
_urn:schemas-upnp-org:service:RenderingControl_event
</eventSubURL>
</service>
</serviceList>
<av:X_RController_DeviceInfo xmlns:av="urn:mi-com:av">
<av:X_RController_Version>1.0</av:X_RController_Version>
<av:X_RController_ServiceList>
<av:X_RController_Service>
<av:X_RController_ServiceType>controller</av:X_RController_ServiceType>
<av:X_RController_ActionList_URL>http://192.168.0.108:6095/</av:X_RController_ActionList_URL>
</av:X_RController_Service>
<av:X_RController_Service>
<av:X_RController_ServiceType>data</av:X_RController_ServiceType>
<av:X_RController_ActionList_URL>http://api.tv.duokanbox.com/bolt/3party/</av:X_RController_ActionList_URL>
</av:X_RController_Service>
</av:X_RController_ServiceList>
</av:X_RController_DeviceInfo>
</device>
<URLBase>http://192.168.0.108:49152/</URLBase>
</root>

四,投屏及控制功能

投屏指令
这里的SOAPAction: "urn:schemas-upnp-org:service:AVTransport:1#SetAVTransportURI" 就是播放指定URL
在SOAP 消息体中 CurrentURI 内容就是播放地址

POST /_urn:schemas-upnp-org:service:AVTransport_control HTTP/1.1
SOAPAction: "urn:schemas-upnp-org:service:AVTransport:1#SetAVTransportURI"
User-Agent: UPnP/1.0 DLNADOC/1.50 Platinum/1.0.5.13
Host: 192.168.0.108:49152
Content-Length: 1535
Content-Type: text/xml; charset="utf-8"


<?xml version="1.0" encoding="UTF-8"?>
<s:Envelope s:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:s="http://schemas.xmlsoap.org/soap/envelope/"><s:Body><u:SetAVTransportURI xmlns:u="urn:schemas-upnp-org:service:AVTransport:1"><InstanceID>0</InstanceID><CurrentURI>http://gslbmgsplive.miguvideo.com/wd_r1/fifa/cctv5hd/720264/encrypt/index.m3u8?msisdn=&amp;mdspid=&amp;spid=800033&amp;netType=4&amp;sid=5500511372&amp;pid=2028597139&amp;timestamp=20180726185704&amp;Channel_ID=0116_23050003-99000-200300020100003&amp;promotionId=&amp;mvid=&amp;mcid=&amp;mpid=&amp;ProgramID=641252154&amp;ParentNodeID=-99&amp;playbackbegin=20180715223000&amp;playbackend=20180716020059&amp;client_ip=223.74.148.1&amp;assertID=5500511372&amp;imei=3d90e97657c1de3de151910495bc22fa6c0bd18914e3b5f7f7e638a25c1bcbbf&amp;chargePhone=&amp;SecurityKey=20180726185704&amp;encrypt=d9814b446d6b3bb25ec6d42a25e59bb0</CurrentURI><CurrentURIMetaData>&lt;DIDL-Lite xmlns="urn:schemas - upnp - org : metadata - 1 - 0 / DIDL - Lite / " xmlns:dc="http ://purl.org/dc/elements/1.1/" xmlns:upnp="urn:schemas-upnp-org:metadata-1-0/upnp/"&gt;&lt;item id="unknown" parentID="-1" restricted="1"&gt;&lt;upnp:genre&gt;Unknown&lt;/upnp:genre&gt;&lt;upnp:storageMedium&gt;UNKNOWN&lt;/upnp:storageMedium&gt;&lt;upnp:writeStatus&gt;UNKNOWN&lt;/upnp:writeStatus&gt;&lt;upnp:class&gt;object.item.videoItem.movie&lt;/upnp:class&gt;&lt;dc:title&gt;unknown&lt;/dc:title&gt;&lt;/item&gt;&lt;/DIDL-Lite&gt;</CurrentURIMetaData></u:SetAVTransportURI></s:Body></s:Envelope>

image.png

查询播放状态指令

投屏指令是向设备描述的处理IP和端口发送TCP http POST指令来完成
比如
<URLBase>http://192.168.0.108:49152/</URLBase>

image.png
POST /_urn:schemas-upnp-org:service:AVTransport_control HTTP/1.1
SOAPAction: "urn:schemas-upnp-org:service:AVTransport:1#GetTransportInfo"
User-Agent: UPnP/1.0 DLNADOC/1.50 Platinum/1.0.5.13
Host: 192.168.0.108:49152
Content-Length: 314
Content-Type: text/xml; charset="utf-8"

<?xml version="1.0" encoding="UTF-8"?>
<s:Envelope s:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:s="http://schemas.xmlsoap.org/soap/envelope/"><s:Body><u:GetTransportInfo xmlns:u="urn:schemas-upnp-org:service:AVTransport:1"><InstanceID>0</InstanceID></u:GetTransportInfo></s:Body></s:Envelope>

这是小米电视响应包

image.png

表示已经开始播放了

HTTP/1.1 200 OK
CONTENT-LENGTH: 411
CONTENT-TYPE: text/xml; charset="utf-8"
DATE: Thu, 26 Jul 2018 10:57:14 GMT
EXT:
SERVER: Linux/3.14.29, UPnP/1.0, Portable SDK for UPnP devices/1.6.13
X-User-Agent: redsonic

<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/" s:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"><s:Body>
<u:GetTransportInfoResponse xmlns:u="urn:schemas-upnp-org:service:AVTransport:1">
<CurrentTransportState>PLAYING</CurrentTransportState>
<CurrentTransportStatus>OK</CurrentTransportStatus>
<CurrentSpeed>1</CurrentSpeed>
</u:GetTransportInfoResponse>
</s:Body> </s:Envelope>

推荐阅读更多精彩内容