⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 socket.cpp

📁 dget是一个基于Linux平台的多线程下载工具, 采用C++开发。主要支持FTP, HTTP, MMS, RTSP协议下载, 目前为止主要实现了FTP, HTTP, MMS,RTSP协议的多线程下载
💻 CPP
字号:
/* * by balancesli * balancesli@gmail.com * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */#include <stdio.h>#include <string.h>#include <stdlib.h>#include <assert.h>#include <errno.h>#include <unistd.h>#include <fcntl.h>#include <sys/types.h>#include <sys/socket.h>#include <sys/utsname.h>#include <netinet/in.h>#include <netdb.h>#include "Utils.h"#include "Socket.h"#include "dget.h"/********************* Class TSocket Impl **********/TSocket :: TSocket(const char * s){	int Len = strlen(s);		Host = new char[Len + 1];	strcpy(Host, s);}TSocket :: ~TSocket(void){	delete [] Host;}char * TSocket :: GetHostName(void) const{	return Host;}void TSocket :: DispAddr(char * Addr){	u_int8_t split[4];	u_int32_t ip;	u_int32_t *x = (u_int32_t *) Addr;	ip = ntohl(*x);	split[0] = (ip & 0xff000000) >> 24;	split[1] = (ip & 0x00ff0000) >> 16;	split[2] = (ip & 0x0000ff00) >> 8;	split[3] = (ip & 0x000000ff);	ShowMsg("%d.%d.%d.%d", split[0], split[1], split[2], split[3]);}	void TSocket :: NsLookup(char * * AddrList, char * HostName){	int i;	for (i = 0; AddrList[i]; i++)	{		ShowMsg(" : ", HostName);		DispAddr(AddrList[i]);	}   	putchar('\n');}	/********************* Class TSocketCli Impl **********/TSocketCli :: TSocketCli(const char * s) : TSocket(s){//	if ((ConnSockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1)	if ((ConnSockfd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1)	{		perror("TSocket failed"); 		exit(EXIT_SUCCESS);	}}TSocketCli :: ~TSocketCli(void){}int TSocketCli :: GetSockfd(void) const{	return ConnSockfd; }uerr_t TSocketCli :: Connect(const int Port){	struct hostent * hp;   	int flags, noblock;	struct sockaddr_in svraddr;	int status;	char * HostName = GetHostName();	//  ShowMsg("Resolving %s\n", HostName);    if ((hp = gethostbyname(HostName)) == NULL)    {		ShowMsg("Failed to resolve %s", HostName);		return HOSTERR;    }		//NsLookup(hp->h_addr_list, hp->h_name);		memset((void *)&svraddr, 0, sizeof(struct sockaddr_in));   	svraddr.sin_family = hp->h_addrtype;   	svraddr.sin_port = htons(Port);	memcpy((void *)&svraddr.sin_addr, hp->h_addr, hp->h_length); 		//Experimental    flags = fcntl(ConnSockfd, F_GETFL, 0);   	if (flags != -1)   		noblock = fcntl(ConnSockfd, F_SETFL, flags | O_NONBLOCK);   	else       	noblock = -1;    //	ShowMsg("Connecting to server.......");    	status = connect(ConnSockfd, (struct sockaddr *)&svraddr,										sizeof(struct sockaddr_in));		if(status == -1 && noblock != -1 && errno == EINPROGRESS)	{	    fd_set writefd;	    struct timeval tv;	    FD_ZERO(&writefd);	    FD_SET(ConnSockfd, &writefd);	    tv.tv_sec = 10;	    tv.tv_usec = 0;	    status = select((ConnSockfd + 1), NULL, &writefd, NULL, &tv);		  	if (status > 0)	  	{	  		socklen_t arglen = sizeof(int);          	if(getsockopt(ConnSockfd, SOL_SOCKET, SO_ERROR, &status, &arglen) < 0)            	status = errno;				            if (status != 0)	            errno = status, status = -1;					        if (errno == EINPROGRESS)	        	errno = ETIMEDOUT;         } 		 else if (status == 0)		    errno = ETIMEDOUT, status = -1;	}		if(status < 0)    {	    close(ConnSockfd);	    if (errno == ECONNREFUSED)	        return CONREFUSED;	    else    	        return CONERROR;	} 	else      {	    flags = fcntl(ConnSockfd, F_GETFL, 0);	    if (flags != -1)	        fcntl(ConnSockfd, F_SETFL, flags & ~O_NONBLOCK);			/*			if (flags != -1)					fcntl( ConnSockfd, F_SETFL, flags | O_NONBLOCK ); */	}	    return NOCONERROR;}/********************* Class TSocketSvr Impl **********/TSocketSvr :: TSocketSvr(const char * s) : TSocket(s){		}TSocketSvr :: ~TSocketSvr(void){}int TSocketSvr :: GetSockfd(void) const{	return ListenSockfd;}uerr_t TSocketSvr :: Bind(void){    struct sockaddr_in svraddr;    /*     * Open a TCP TSocket (an Internet stream TSocket).     */    if ((ListenSockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0)    {		return CONSOCKERR;    }    /*     * Fill in structure fields for binding     */    memset((void *) &svraddr, 0, sizeof(struct sockaddr_in));	    svraddr.sin_family = AF_INET;    svraddr.sin_addr.s_addr = htonl(INADDR_ANY);    svraddr.sin_port = htons(0);		    /*     * bind the address to the TSocket     */	if(bind(ListenSockfd, (struct sockaddr *)&svraddr, 								sizeof(struct sockaddr_in)) < 0)    {		perror("bind");		close(ListenSockfd);		return BINDERR;    }    /*     * allow only one server      */    if (listen(ListenSockfd, 1) < 0)    {		perror("listen");		close(ListenSockfd);		return LISTENERR;    }    return BINDOK;}uerr_t TSocketSvr :: Accept(int * DataSock){    struct sockaddr_in cliaddr;	   	socklen_t len = sizeof(struct sockaddr_in);		int skfd = accept(ListenSockfd, (struct sockaddr *)&cliaddr, &len);    	if (skfd < 0)    {		perror("accept");		return ACCEPTERR;    }		*DataSock = skfd;    	/*     * now we can free the listen TSocket since it is not needed...     * accept returnd the new TSocket...      */	close(ListenSockfd);    	return ACCEPTOK;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -