(一)onvif- remotediscovery测试
来源:互联网 发布:安卓解压软件 编辑:程序博客网 时间:2024/06/15 02:03
刚开始研究,参考了网上的代码,但是出现了错误!还有很多问题慢慢理解吧!记录今天的发现。
gsoap版本:2.8.32最新版本
下载onvif的wsdl文件生成c文件。
感谢此博客的博主,http://gaohtao.blog.163.com/blog/#m=0&t=3&c=onvif
从头说起:
1、下载gsoap,解压后进入目录:
./configure <> make
gsoap\src 以及\gsoap\wsdl下可见生成onvif架构的可执行文件!——soapcpp2和wsdl2h可执行文件
2、利用上面两个可执行文件生成onvif代码如下:
首先可以下载onvif的wsdl文件,下载方法:
http://www.onvif.org/onvif/ver20/util/operationIndex.html
比如下载devicemgmt.wsdl,对准DeviceMgmt下的比如GetDeviceInformation链接右键链接另存为即可出现!保存就好了,其他的下载方法一样!
DeviceMgmt
GetDeviceInformation 。。。
拷贝soapcpp2和wsdl2h到bin的linui386目录下(自己建立,可以自己建立,具体位置也无所谓),如果该目录有此文件就不必拷贝了,如果运行不了在拷贝!
使用wsdl2h生成对应h文件。注意拷贝wsdl目录下的typemap.dat以及下载回来的remotediscovery.wsdl到的bin/linuxi386目录下,只用remotediscovey.wsdl。后面在研究其他的把
./wsdl2h -o remotediscovery.h -c -s -t typemap.dat remotediscovery.wsdl
生成C文件
./soapcpp2 remotediscovery.h -x -I ../../import3、从网上download代码下来,具体代码不列出来了,编译后执行
sudo ./onvifserver
在ONVIF Device Test tool 按device discovery 按钮没有发现,输入IP后,按probe后弹出如下错误框
—————————————————————————————
| |
| Unexpected error occurred:XML文档(2,833)中有错误。 |
| |
—————————————————————————————
重新编译gsoap后又出现如下bug
—————————————————————————————
| |
| Unexpected error occurred:XML文档(2,909)中有错误。 |
| |
—————————————————————————————
解决方法:查找到sendto函数看看onvif回复的信息,使用GDB调试;
GDB小技巧:
通常在gdb调试时要打印出一些字符串的内容,通过
p str@str_len 打印字符串时,通常有长度的限制,我测试linux机器上默认为200个,但实际输出的长度str_len可能大于该值。
结果不能够完全输出,而进行了省略,通过命令set print element 0就可以了。
使用wireshark解析,过滤方法:(ip.addr eq 10.104.15.230 and ip.addr eq 10.104.15.50) and (udp.port eq 3702 and udp.port eq 3702)
分析ONVIF Device Test tool发送的数据以及discoveryserver回复的数据对比!
ONVIF Device Test tool发送的数据,发两次数据如下:
<?xml version="1.0" encoding="utf-8"?><Envelope xmlns:tds="http://www.onvif.org/ver10/device/wsdl" xmlns="http://www.w3.org/2003/05/soap-envelope"><Header><wsa:MessageID xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing">uuid:ac68cf08-25da-465c-97f1-ac6da5efc4d9</wsa:MessageID><wsa:To xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing">urn:schemas-xmlsoap-org:ws:2005:04:discovery</wsa:To><wsa:Action xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing">http://schemas.xmlsoap.org/ws/2005/04/discovery/Probe</wsa:Action></Header><Body><Probe xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns:xsd="http://www.w3.org/2001/XMLSchema"xmlns="http://schemas.xmlsoap.org/ws/2005/04/discovery"><Types>tds:Device</Types><Scopes><Scopes /></Probe></Body></Envelope>
<?xml version="1.0" encoding="utf-8"?><Envelope xmlns:dn="http://www.onvif.org/ver10/network/wsdl" xmlns="http://www.w3.org/2003/05/soap-envelope"><Header><wsa:MessageID xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing">uuid:b02cab32-f5bc-4bfa-b968-0f4b0a228208</wsa:MessageID><wsa:To xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing">urn:schemas-xmlsoap-org:ws:2005:04:discovery</wsa:To><wsa:Action xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing">http://schemas.xmlsoap.org/ws/2005/04/discovery/Probe</wsa:Action></Header><Body><Probe xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://schemas.xmlsoap.org/ws/2005/04/discovery"><Types>dn:NetworkVideoTransmitter</Types><Scopes /></Probe></Body></Envelope>
onvifserver回复的数据如下:
<?xml version="1.0" encoding="UTF-8"?><SOAP-ENV:Envelope xmlns:SOAP-ENV="http://www.w3.org/2003/05/soap-envelope" xmlns:SOAP-ENC="http://www.w3.org/2003/05/soap-encoding" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing" xmlns:wsdd="http://schemas.xmlsoap.org/ws/2005/04/discovery" xmlns:tdn="http://www.onvif.org/ver10/network/wsdl"><SOAP-ENV:Header><wsa:MessageID>uuid:2419d68a-2dd2-21b2-a205-010101010101</wsa:MessageID><wsa:RelatesTo>uuid:3a7c78e4-bacb-4ec8-a4ee-225e5e575a41</wsa:RelatesTo><wsa:To SOAP-ENV:mustUnderstand="true">http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous</wsa:To><wsa:Action SOAP-ENV:mustUnderstand="true">http://schemas.xmlsoap.org/ws/2005/04/discovery/ProbeMatches</wsa:Action></SOAP-ENV:Header><SOAP-ENV:Body><wsdd:ProbeMatches><SOAP-RPC:result xmlns:SOAP-RPC="http://www.w3.org/2003/05/soap-rpc">-sizeProbeMatch</SOAP-RPC:result><wsdd:ProbeMatch xmlns:_0="http://www.onvif.org/ver10/device/wsdl"><wsa:EndpointReference><wsa:Address>urn:uuid:2419d68a-2dd2-21b2-a205-010101010101</wsa:Address><wsa:ReferenceProperties></wsa:ReferenceProperties><wsa:ReferenceParameters></wsa:ReferenceParameters><wsa:PortType>ttl</wsa:PortType></wsa:EndpointReference><wsdd:Types>_0:Device</wsdd:Types><wsdd:Scopes>onvif://www.onvif.org/type/NetworkVideoTransmitter</wsdd:Scopes><wsdd:XAddrs>http://010.104.15.230/onvif/device_service</wsdd:XAddrs><wsdd:MetadataVersion>1</wsdd:MetadataVersion></wsdd:ProbeMatch></wsdd:ProbeMatches></SOAP-ENV:Body></SOAP-ENV:Envelope
ONVIF Device Test tool提示的错误:
Unexpected error occurred:XML文档(2,909)中有错误
是discoveryserver回复的XML文件有错误,偏移位置909,定位至909,为:
<SOAP-RPC:result xmlns:SOAP-RPC="http://www.w3.org/2003/05/soap-rpc">-sizeProbeMatch</SOAP-RPC:result>
这句有错误。查看代码定位置-sizeProbeMatch字符串,调试具体代码如下:
SOAP_FMAC3 int SOAP_FMAC4 soap_out_wsdd__ProbeMatchesType(struct soap *soap, const char *tag, int id, const struct wsdd__ProbeMatchesType *a, const char *type){(void)soap; (void)tag; (void)id; (void)a; (void)type; /* appease -Wall -Werror */if (soap_element_begin_out(soap, tag, soap_embedded_id(soap, id, a, SOAP_TYPE_wsdd__ProbeMatchesType), type))return soap->error;printf("function:%s,line:%d \n",__FUNCTION__,__LINE__);soap_element_result(soap, "-sizeProbeMatch");//if (a->ProbeMatch){int i;for (i = 0; i < (int)a->__sizeProbeMatch; i++)if (soap_out_wsdd__ProbeMatchType(soap, "wsdd:ProbeMatch", -1, a->ProbeMatch + i, ""))return soap->error;}return soap_element_end_out(soap, tag);}
定位函数soap_element_result(soap, "-sizeProbeMatch");
屏蔽次函数即可,就不会发送<SOAP-RPC:result xmlns:SOAP-RPC="http://www.w3.org/2003/05/soap-rpc">-sizeProbeMatch</SOAP-RPC:result>这个了,一切正常!
点击Onvif Device test tool的Discover Devices无法枚举,原因如下:
分析:使用wireshark由于Discover Devices点击会发送的是组播信息,使用GDB调试程序发现一直停在了recvfrom函数,对组播信息完全忽略。跟踪发现soap_bind如下代码:
if (soap_valid_socket(soap->master)){ soap->fclosesocket(soap, soap->master); soap->master = SOAP_INVALID_SOCKET;}soap->fclosesocket(soap, soap->master);
//linux下调用close,也就是会把之前申请的关闭了,所以之前对socket加入组播信息也会没有,如果要重新识别组播信息,就必须重新加入组播,
//所以在bind后面必要重新加入组播代码如下:
struct ip_mreq mreq; mreq.imr_multiaddr.s_addr = inet_addr("239.255.255.250"); mreq.imr_interface.s_addr = htonl(INADDR_ANY); if(setsockopt(server_udp,IPPROTO_IP,IP_ADD_MEMBERSHIP,&mreq,sizeof(mreq))==-1){ _DBG_ERROR("memberchip error\n"); }原主函数:
int main{int server_udp;int retval=0;struct soap *soap_udp;int fault_flag = 0;server_udp = create_server_socket_udp();bind_server_udp1(server_udp);while(1){soap_udp=soap_new();//soap_init(soap_udp);soap_init1(soap_udp, SOAP_IO_UDP);soap_udp->master = server_udp;soap_udp->socket = server_udp;printf("skfd:%d \n",server_udp);soap_udp->errmode = 0;soap_udp->bind_flags = 1;if (!soap_valid_socket(soap_bind(soap_udp, NULL, UDP_PORT, 100))){ soap_print_fault(soap_udp, stderr);}printf("%d \n",soap_udp->master);PRINT_MSG("soap_serve starting..\n");retval = soap_serve(soap_udp); if(retval && !(fault_flag)){fault_flag = 1;}else if(!retval){fault_flag = 0;}soap_destroy(soap_udp);soap_end(soap_udp);soap_done(soap_udp);free(soap_udp);}}
新的主函数:
int main{int server_udp;int retval=0;struct soap *soap_udp;int fault_flag = 0;server_udp = create_server_socket_udp();bind_server_udp1(server_udp);while(1){soap_udp=soap_new();soap_init1(soap_udp, SOAP_IO_UDP);soap_udp->master = server_udp;soap_udp->socket = server_udp;soap_udp->errmode = 0;soap_udp->bind_flags = 1;if (!soap_valid_socket(soap_bind(soap_udp, NULL, UDP_PORT, 100))){ soap_print_fault(soap_udp, stderr);}//重新加入组播#define 1struct ip_mreq mreq;mreq.imr_multiaddr.s_addr = inet_addr("239.255.255.250");mreq.imr_interface.s_addr = htonl(INADDR_ANY);if(setsockopt(server_udp,IPPROTO_IP,IP_ADD_MEMBERSHIP,&mreq,sizeof(mreq))==-1){ _DBG_ERROR("memberchip error\n");}#endifPRINT_MSG("soap_serve starting..\n");retval = soap_serve(soap_udp); if(retval && !(fault_flag)){fault_flag = 1;}else if(!retval){fault_flag = 0;}soap_destroy(soap_udp);soap_end(soap_udp);soap_done(soap_udp);free(soap_udp);}}
- (一)onvif- remotediscovery测试
- 转载 CSDN上的 onvif协议的设备发现实现代码 RemoteDiscovery
- onvif测试工具使用方法
- onvif 上手(一)
- Onvif裁剪(一)
- ONVIF测试方法及工具
- ONVIF测试方法及工具
- onvif 笔记一(gsoap)
- gSOAP+onvif初探(一):生成onvif代码框架
- Onvif
- ONVIF
- Onvif
- onvif
- ONVIF
- onvif
- onvif 设备自发现测试通过
- onvif 设备自发现测试通过
- onvif测试工具的使用教程
- 聊聊并发(四)——深入分析ConcurrentHashMap
- Android:onClick 底层属性调用
- 关于数列an=n^t(t为常数)前n项求和公式的讨论
- 75. Sort Colors
- Android transformClassesWithDexForAdh5Debug 的解决方法
- (一)onvif- remotediscovery测试
- MPU6050在ROS中应用
- 最全Python爬虫总结
- 设计模式之装饰者模式
- Linux堆内存管理深入分析
- JavaWeb学习总结(十二)——Session
- J2SE:总结—基础很重要哈!
- linux下的简单计算器bc
- Java类集介绍