Linux socket 类封装 (面向对象方法)

 1 /*
 2  * socketfactory.h
 3  *
 4  *  Created on: 2014-7-19
 5  *      Author: root
 6  */
 7 
 8 #ifndef SOCKETFACTORY_H_
 9 #define SOCKETFACTORY_H_
10 #include<sys/types.h>
11 
12 /*
13  * 在网路编程中, 一般分为服务端和客户端,两者的行为有相似之处,也有非常多的不同。在linux中对socket程序设计
14  * 仅提供了socket(), bind(), connection(), accept() listern() 几个函数,并未区分是服务端还是客户端。
15  * 在java或其他高级语言中,一般都对socket进行了封装,简化使用。
16  *  此端程序将linux socket进行封装在三个类中。一个工厂类,两个接口类。
17  *
18  */
19 
20 namespace socketfactory {
21 
22 class ISocket;
23 class IServerSocket;
24 
25 /*
26  * SocketFactory 负责创建 ISocket, IServerSocket 的实例,同时负责销毁实例。
27  * SocketFactory的方法全部是静态方法。此处采用了工厂模式。
28  *
29   */
30 class SocketFactory {
31 public:
32     static ISocket* createSocket(const char* tIP, int tPort);    /* 创建客户端 socket */
33     static IServerSocket* createServerSocket(int port);            /* 创建服务端 socket */
34     static int destroy(ISocket* psocket);                                /* 销毁 */
35     static int destroy(IServerSocket* psocket);                        /* 销毁 */
36 };
37 
38 /*
39  * ISocket 为接口,定义为纯虚类。面向接口编程
40  *
41  */
42 
43 class ISocket {
44 public:
45     virtual int read(void* buf, size_t len)=0;        /*    读取对端数据 */
46     virtual int write(void* buf, size_t len)=0;        /* 写入对端数据 */
47     virtual int close()=0;                                    /* 关闭连接 */
48 };
49 
50 /*
51  * IServerSocket 为接口,定义为纯虚类。面向接口编程。
52  *
53  */
54 
55 class IServerSocket {
56 public:
57     virtual ISocket* accept()=0;                        /* 接受连接,返回与对端通信的socket */
58     virtual int listen(int backlog)=0;                /*    启动服务端口 监听 */
59     virtual int close()=0;                                /* 关闭 服务端 socket */
60 };
61 
62 }
63 
64 #endif /* SOCKETFACTORY_H_ */

 

实现类的头文件

 1 /*
 2  * socketimpl.h
 3  *
 4  *  Created on: 2014-7-20
 5  *      Author: root
 6  */
 7 
 8 #ifndef SOCKETIMPL_H_
 9 #define SOCKETIMPL_H_
10 #include <sys/socket.h>
11 #include <netinet/in.h>
12 #include "socketfactory.h"
13 
14 using namespace socketfactory;
15 
16 /*
17  * ISocket 和 IServerSocket 的实现类。
18  *  SocketFactory工厂类创建这些实现类。
19  *
20  */
21 
22 class SocketImpl: public ISocket
23 {
24 public:
25     int read(void* buf, size_t len);
26     int write(void* buf, size_t len);
27     int close();
28 
29     int ssocket(int domain, int type, int protocol);
30     int cconnect(int sockfd, const struct sockaddr *addr, socklen_t addrlen);
31     SocketImpl();
32     virtual ~SocketImpl();
33 
34 public:
35     int fd;
36     struct sockaddr  address;
37 };
38 
39 
40 class ServerSocketImpl: public IServerSocket
41 {
42 public:
43     ISocket* accept();
44     int listen(int backlog);
45     int close();
46 
47 
48     int ssocket(int domain, int type, int protocol);
49     int bbind(int sockfd, const struct sockaddr *addr, socklen_t addrlen);
50     ServerSocketImpl();
51     virtual ~ServerSocketImpl();
52 
53 public:
54     int fd;
55     struct sockaddr  address;
56 };
57 
58 
59 #endif /* SOCKETIMPL_H_ */

 

  1 /*
  2  * socketimpl.cpp
  3  *
  4  *  Created on: 2014-7-20
  5  *      Author: root
  6  */
  7 
  8 #include <unistd.h>
  9 #include "socketimpl.h"
 10 #include <sys/types.h>
 11 #include <sys/socket.h>
 12 
 13 #include <stdio.h>
 14 
 15 
 16 SocketImpl::SocketImpl() {
 17     this->fd = -1;
 18 }
 19 
 20 int SocketImpl::ssocket(int domain, int type, int protocol) {
 21     this->fd = socket(domain, type, protocol);
 22     if (this->fd < 0)
 23         perror("SocketImpl::ssocket");
 24     return this->fd;
 25 }
 26 
 27 int SocketImpl::cconnect(int sockfd, const struct sockaddr *addr,
 28         socklen_t addrlen) {
 29     int ret = connect(sockfd, addr, addrlen);
 30     if (ret != 0)
 31         perror("SocketImpl::cconnect");
 32     return ret;
 33 
 34 }
 35 
 36 SocketImpl::~SocketImpl() {
 37 
 38 }
 39 
 40 int SocketImpl::read(void* buf, size_t len) {
 41     int ret = ::read(this->fd, buf, len);
 42     if (ret < 0)
 43         perror("SocketImpl::read");
 44     return ret;
 45 }
 46 ;
 47 
 48 int SocketImpl::write(void* buf, size_t len) {
 49     int ret = ::write(this->fd, buf, len);
 50     if (ret < 0)
 51         perror("SocketImpl::write");
 52     return ret;
 53 }
 54 ;
 55 
 56 int SocketImpl::close() {
 57     if (this->fd > 0) {
 58         int ret = ::close(this->fd);
 59         if (ret != 0)
 60         {
 61             perror("SocketImpl::close");
 62             return ret;
 63         }else
 64             this->fd = -1;
 65     }
 66     return 0;
 67 }
 68 
 69 ServerSocketImpl::ServerSocketImpl() {
 70     this->fd = 0;
 71 }
 72 
 73 ServerSocketImpl::~ServerSocketImpl() {
 74 }
 75 
 76 int ServerSocketImpl::ssocket(int domain, int type, int protocol) {
 77     this->fd = socket(domain, type, protocol);
 78     if (this->fd < 0)
 79         perror("ServerSocketImpl::ssocket");
 80     return this->fd;
 81 }
 82 
 83 int ServerSocketImpl::bbind(int sockfd, const struct sockaddr *addr,
 84         socklen_t addrlen) {
 85     int ret = bind(this->fd, addr, addrlen);
 86     if (ret < 0)
 87         perror("ServerSocketImpl::bbind");
 88     return ret;
 89 }
 90 
 91 ISocket* ServerSocketImpl::accept() {
 92     SocketImpl* nsocket = new SocketImpl();
 93     int addlen=0;
 94     int nfd =  ::accept(this->fd, &nsocket->address, (socklen_t*)&addlen);
 95     if (nfd == -1) {
 96         delete nsocket;
 97         perror("ServerSocketImpl::accept");
 98         return NULL;
 99     }
100     nsocket->fd = nfd;
101     return nsocket;
102 }
103 
104 int ServerSocketImpl::listen(int backlog) {
105     int ret = ::listen(this->fd, backlog);
106     if (ret < 0)
107         perror("ServerSocketImpl::listen");
108     return ret;
109 }
110 
111 int ServerSocketImpl::close() {
112     if(this->fd >0 )
113     {
114         int ret=::close(this->fd);
115         if(ret!=0 )
116         {
117             perror("ServerSocketImpl::close");
118             return ret;
119         }else
120             this->fd =-1;
121     }
122     return 0;
123 }

 

/*
 * socketfactory.cpp
 *
 *  Created on: 2014-7-20
 *      Author: root
 */

#include "socketfactory.h"
#include "socketimpl.h"

#include <sys/socket.h>
#include <netinet/in.h>
#include <string.h>
#include <stdio.h>
#include <arpa/inet.h>


ISocket* SocketFactory::createSocket(const char* tIP, int tPort)
{
    SocketImpl*  nsocket=new SocketImpl();
    memset(&nsocket->address, 0, sizeof(sockaddr));
    struct sockaddr_in* padd=(sockaddr_in*)(&nsocket->address);
    padd->sin_family=AF_INET;
    padd->sin_port=htons(tPort);
    if( inet_pton(AF_INET, tIP, &padd->sin_addr) <= 0){
        delete nsocket;
        perror("SocketFactory::createSocket:inet_pton");
        return NULL;
    }
    int ret=nsocket->ssocket(AF_INET, SOCK_STREAM, 0);
    if(ret < 0 ){
        perror("SocketFactory::createSocket:ssocket");
        delete nsocket;
        return NULL;
    }
    ret=nsocket->cconnect(nsocket->fd, &nsocket->address, sizeof(sockaddr));
    if(ret < 0 ){
        perror("SocketFactory::createSocket:cconnect");
        nsocket->close();
        delete nsocket;
        return NULL;
    }
    return nsocket;
}

IServerSocket* SocketFactory::createServerSocket(int port)
{
    ServerSocketImpl *nssocket=new ServerSocketImpl();
    memset(&nssocket->address, 0, sizeof(sockaddr));
    struct sockaddr_in* padd=(sockaddr_in*)(&nssocket->address);
    padd->sin_family=AF_INET;
    padd->sin_addr.s_addr=htonl(INADDR_ANY);
    padd->sin_port=htons(port);
    int ret=nssocket->ssocket(AF_INET, SOCK_STREAM, 0);
    if(ret<0){
        perror("SocketFactory::createServerSocket:ssocket");
        delete nssocket;
        return NULL;
    }
    ret=nssocket->bbind(nssocket->fd, &nssocket->address, sizeof(sockaddr));
    if(ret<0){
        perror("SocketFactory::createServerSocket:bbind");
        nssocket->close();
        delete nssocket;
        return NULL;
    }
    return nssocket;
}

int SocketFactory::destroy(ISocket* psocket)
{
    SocketImpl* psockimpl=(SocketImpl*)psocket;
    psockimpl->close();
    delete psockimpl;
    return 0;
}

int SocketFactory::destroy(IServerSocket* psocket)
{
    ServerSocketImpl* pssocket=(ServerSocketImpl*)psocket;
    pssocket->close();
    delete pssocket;
    return 0;
}

郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。