muduo之EventLoopThread

         muduo用EventLoopThread提供了对应eventloop和thread的封装,意为I/O线程类,EventLoopThread可以创建一个IO线程,通过startLoop返回一个IO线程的loop,threadFunc中开启loop循环,其中的API涉及一些多线程中的互斥量和条件变量的操作。

EventLoopThread.h

// Copyright 2010, Shuo Chen.  All rights reserved.
// http://code.google.com/p/muduo/
//
// Use of this source code is governed by a BSD-style license
// that can be found in the License file.

// Author: Shuo Chen (chenshuo at chenshuo dot com)
//
// This is a public header file, it must only include public header files.

#ifndef MUDUO_NET_EVENTLOOPTHREAD_H
#define MUDUO_NET_EVENTLOOPTHREAD_H

#include "muduo/base/Condition.h"
#include "muduo/base/Mutex.h"
#include "muduo/base/Thread.h"

namespace muduo
{
namespace net
{

class EventLoop;

//I/O线程类,线程池启动IO线程
class EventLoopThread : noncopyable
{
 public:
  typedef std::function<void(EventLoop*)> ThreadInitCallback;

  EventLoopThread(const ThreadInitCallback& cb = ThreadInitCallback(),
                  const string& name = string());
  ~EventLoopThread();
  EventLoop* startLoop();         //启动成员thread_线程,该线程就成了I/O线程,内部调用thread_.start()

 private:
  void threadFunc();            //线程运行函数

  EventLoop* loop_ GUARDED_BY(mutex_);      		//loop_指针指向一个EventLoop对象
  bool exiting_;
  Thread thread_;
  MutexLock mutex_;
  Condition cond_ GUARDED_BY(mutex_);
  ThreadInitCallback callback_;               //回调函数在EventLoop::loop事件循环之前被调用
};

}  // namespace net
}  // namespace muduo

#endif  // MUDUO_NET_EVENTLOOPTHREAD_H

EventLoopThread.cc

// Copyright 2010, Shuo Chen.  All rights reserved.
// http://code.google.com/p/muduo/
//
// Use of this source code is governed by a BSD-style license
// that can be found in the License file.

// Author: Shuo Chen (chenshuo at chenshuo dot com)

#include "muduo/net/EventLoopThread.h"

#include "muduo/net/EventLoop.h"

using namespace muduo;
using namespace muduo::net;

EventLoopThread::EventLoopThread(const ThreadInitCallback& cb,
                                 const string& name)
  : loop_(NULL),      //loop未启动为NULL
    exiting_(false),
    thread_(std::bind(&EventLoopThread::threadFunc, this), name),   //绑定线程运行函数
    mutex_(),
    cond_(mutex_),
    callback_(cb)
{
}

EventLoopThread::~EventLoopThread()
{
  exiting_ = true;
  if (loop_ != NULL) // not 100% race-free, eg. threadFunc could be running callback_.
  {
    // still a tiny chance to call destructed object, if threadFunc exits just now.
    // but when EventLoopThread destructs, usually programming is exiting anyway.
    loop_->quit();
    thread_.join();   //等待线程退出
  }
}

EventLoop* EventLoopThread::startLoop()
{
  assert(!thread_.started());
  thread_.start(); //调用pthread_create创建线程,此时有两个线程在运行
  //一个是调用EventLoopThread::startLoop()的线程,一个是执行EventLoopThread::threadFunc()的线程(IO线程)

  EventLoop* loop = NULL;
  {
    MutexLockGuard lock(mutex_);
    while (loop_ == NULL)
    {
      cond_.wait();     //须要等待EventLoop对象的创建
    }
    loop = loop_;       //IO线程创建loop_赋给主线程
  }
  
  return loop;          //主线程返回IO线程创建的EventLoop对象
}

void EventLoopThread::threadFunc()            //创建线程时会调用这个函数
{
  EventLoop loop;       //IO线程也要创建EventLoop对象,还要通知主线程已经创建完毕

  if (callback_)
  {
    callback_(&loop);     //将定义好的loop传入回调
  }

  {
    MutexLockGuard lock(mutex_);
    // loop_指针指向了一个栈上的对象,threadFunc函数退出之后。这个指针就失效了
    // threadFunc函数退出,就意味着线程退出了,EventLoopThread对象也就没有存在的价值了
    // 因而不会有什么大的问题
    loop_ = &loop;
    cond_.notify();     //创建好,发送通知
  }

  loop.loop();          // 会在这里循环,直到EventLoopThread析构。此后不再使用loop_訪问EventLoop了
  //assert(exiting_);
  MutexLockGuard lock(mutex_);
  loop_ = NULL;
}

 

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

盼盼编程

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值