Muduo源码刨析-建立连接的acceptor类

Acceptor类

 Muduo中的acceptor类是对accept的一层简单封装,对外只提供listen接口和setNewConnectionCallnack接口

Acceptor类功能

 实现对连接的accept并且调用持有该acceptor的类的newconnection来创建持有者想要连接

接口

	///把fd和地址信息传递出去
	typedef std::function<void (int, const InetAddress&)> NewConnectionCallback;
 	void setNewConnectionCallBack(const NewConnectionCallback& cb);

    void listen();

    bool isListening() const{
        return m_isListen;
    }

数据成员

	void handleRead();
    
    EventLoop *m_loop;///所属loop
    Socket m_listenSocket;///监听的fd
    Channel m_readChannel;///管理的channel
    NewConnectionCallback m_acceptCb;
    bool m_isListen;
    int m_idleFd;

具体实现

CzyNetFrame::Acceptor::Acceptor(EventLoop *loop, const InetAddress &listenAddr, bool reusePort)
    : m_loop(loop), m_listenSocket(sockets::createNonblockingOrDie(listenAddr.family())),
      m_readChannel(m_loop, m_listenSocket.fd()), m_idleFd(::open("/dev/null", O_RDONLY | O_CLOEXEC))
{
    assert(m_idleFd >= 0);
    m_listenSocket.setReusePort(reusePort);
    m_listenSocket.setReuseAddr(true);
    m_listenSocket.bindAddress(listenAddr);
    m_readChannel.setReadCb(std::bind(&Acceptor::handleRead, this));
}

构造函数只干三件事:1.设置好监听的socket,2.将处理读的channel绑定到属主loop上,3.设置好readChannel的读回调

void CzyNetFrame::Acceptor::listen()
{
    m_loop->assertInLoopThread();
    m_isListen = true;
    m_listenSocket.listen();
    m_readChannel.enableRead();
}

listen函数是暴露给外的接口,启动listen,并且通过channel对对方发起的连接的读事件改为感兴趣的状态

void CzyNetFrame::Acceptor::handleRead()
{
    m_loop->assertInLoopThread();
    InetAddress peerAddr;
    int connfd = m_listenSocket.accept(&peerAddr);
    if (connfd >= 0)
    {
        if (m_acceptCb)
        {
            m_acceptCb(connfd, peerAddr);
        }
        else
        {
            sockets::close(connfd);
        }
    }
    else
    {
        LOG_SYSERR << " in acceptor ::handleRead too many connfd";
        this tricks to defend two many client
        if (errno == EMFILE)
        {
            ::close(m_idleFd);
            m_idleFd = ::accept(m_listenSocket.fd(), NULL, NULL);
            ::close(m_idleFd);
            m_idleFd = ::open("/dev/null", O_RDONLY | O_CLOEXEC);
        }
    }
}

handleRead则实实在在的调用了linux系统下的accept,并且掉用通过设置的newConnection设置的回调

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值