x265-1.7版本-common/threadpool.h注释
来源:互联网 发布:c语言调用linux命令 编辑:程序博客网 时间:2024/06/15 15:27
注:问号以及未注释部分 会在x265-1.8版本内更新
/***************************************************************************** * Copyright (C) 2013 x265 project * * Authors: Steve Borho <steve@borho.org> * * 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., 51 Franklin Street, Fifth Floor, Boston, MA 02111, USA. * * This program is also available under a commercial proprietary license. * For more information, contact us at license @ x265.com *****************************************************************************/#ifndef X265_THREADPOOL_H#define X265_THREADPOOL_H#include "common.h"#include "threading.h"namespace x265 {// x265 private namespaceclass ThreadPool;class WorkerThread;class BondedTaskGroup;#if X86_64typedef uint64_t sleepbitmap_t;#elsetypedef uint32_t sleepbitmap_t;#endifstatic const sleepbitmap_t ALL_POOL_THREADS = (sleepbitmap_t)-1;enum { MAX_POOL_THREADS = sizeof(sleepbitmap_t) * 8 };enum { INVALID_SLICE_PRIORITY = 10 }; // a value larger than any X265_TYPE_* macro// Frame level job providers. FrameEncoder and Lookahead derive from// this class and implement findJob()class JobProvider{public: ThreadPool* m_pool; //指向encoder类中的m_threadPool sleepbitmap_t m_ownerBitmap; //当前任务拥有的核 //ALL_POOL_THREADS = -1 sleepbitmap_t 为无符号数64位整数,初始化为0 //这是一个map,如4核机器:cup(0,1,2,3) 对应 (1,10,100,1000),查看当前哪些位置是1表示当前哪个cpu在干活,如果是4核,最大值当然就是1111,15 //在函数JobProvider::tryWakeOne()和WorkerThread::threadMain()会对其改变 在tryWakeOne()中,将释放当前其不应该拥有的id,重新更新map int m_jpId; //其对应的jobid,一个任务一个id如:4核单机中:m_frameEncoder[0] m_jpId:0 m_frameEncoder[1] m_jpId:1 m_lookahead m_jpId:2 int m_sliceType; //???在FrameEncoder类中表示其帧类型 bool m_helpWanted; //初始化为false,会在JobProvider::tryWakeOne()、WaveFront::findJob(int threadId)、 Lookahead::findJob()中有更新 //Lookahead::findJob()中:如果当前还不能进行帧类型决策,则将其置为false,表示暂不需要核 //JobProvider::tryWakeOne() 中,如果当前没有返回可用的mid(核),则置为true,表示需要核 //WaveFront::findJob(int threadId)??? bool m_isFrameEncoder; // 当前子类是否是FrameEncoder,在创建子类FrameEencoder时候会对该值进行赋值/* rather ugly hack, but nothing better presents itself */ JobProvider() : m_pool(NULL) , m_ownerBitmap(0) , m_jpId(-1) , m_sliceType(INVALID_SLICE_PRIORITY) , m_helpWanted(false) , m_isFrameEncoder(false) {} virtual ~JobProvider() {} // Worker threads will call this method to perform work virtual void findJob(int workerThreadId) = 0; // Will awaken one idle thread, preferring a thread which most recently // performed work for this provider. void tryWakeOne();};class ThreadPool{public: sleepbitmap_t m_sleepBitmap;// 用于记录当前哪些核是sleep,其对应位为1的 ,一开始拥有全部的全部为sleep (例如四核机器:一般是0~15的数据) // 在函数tryAcquireSleepingThread 和WorkerThread::threadMain()会对其改变 int m_numProviders;//当前提供给几个线程 如: 0 frameEncode[0] 1 frameEncoder[1] 2 lookachead int m_numWorkers;//当前机器核数 单机4核测试是4 int m_numaNode; bool m_isActive; JobProvider** m_jpTable; WorkerThread* m_workers; ThreadPool(); ~ThreadPool(); bool create(int numThreads, int maxProviders, int node); bool start(); void stopWorkers(); /** 函数功能 :设置线程间能够在不同的核运行,而不会同时占用同一个核 /* 调用范围 :只在 WorkerThread::threadMain()和FrameEncoder::threadMain()函数中被调用 * \参数 numaNode :表示当前处于node的位置,如果没有配置,则只有一个就是0 * \返回 :null * */ void setCurrentThreadAffinity(); /** 函数功能 :在tryWakeOne中返回当前机器任意一个正在睡眠的核,tryBondPeers返回当前线程拥有核且正在睡眠的核 /* 调用范围 :只在 JobProvider::tryWakeOne()和ThreadPool::tryBondPeers函数中被调用 * \参数 firstTryBitmap :为Job的m_ownerBitmap (如4核机器:一般传入是-1~15的数据) * \参数 secondTryBitmap :只有0 和 -1 两个值能够传进来,tryBondPeers为0 tryWakeOne() 为-1(全为1,mask值) * \返回 :在tryWakeOne中返回当前机器任意一个正在睡眠的核,tryBondPeers返回当前线程拥有核且正在睡眠的核 * */ int tryAcquireSleepingThread(sleepbitmap_t firstTryBitmap, sleepbitmap_t secondTryBitmap); /** 函数功能 : 返回当前可用核数,并在threadmain中触发相应processtask /* 调用范围 : 只在slicetypeDecide、CostEstimateGroup::finishBatch()、CostEstimateGroup::estimateFrameCost、predInterSearch、compressFrame()和compressInterCU_dist函数中被调用 * \返回 : 返回当前可用核数 * */ int tryBondPeers(int maxPeers, sleepbitmap_t peerBitmap, BondedTaskGroup& master); static ThreadPool* allocThreadPools(x265_param* p, int& numPools); static int getCpuCount(); static int getNumaNodeCount(); /** 函数功能 :设置线程间能够在不同的核运行,而不会同时占用同一个核 /* 调用范围 :只在 ThreadPool::setCurrentThreadAffinity()函数中被调用 * \参数 numaNode :表示当前处于node的位置,如果没有配置,则只有一个就是0 * \返回 :null * */ static void setThreadNodeAffinity(int node);};/* Any worker thread may enlist the help of idle worker threads from the same * job provider. They must derive from this class and implement the * processTasks() method. To use, an instance must be instantiated by a worker * thread (referred to as the master thread) and then tryBondPeers() must be * called. If it returns non-zero then some number of slave worker threads are * already in the process of calling your processTasks() function. The master * thread should participate and call processTasks() itself. When * waitForExit() returns, all bonded peer threads are quarunteed to have * exitied processTasks(). Since the thread count is small, it uses explicit * locking instead of atomic counters and bitmasks */class BondedTaskGroup //被PMODE、WeightAnalysis、PME、CostEstimateGroup、PreLookaheadGroup继承{public: Lock m_lock; //在多线程操作中获取临界资源时用于加锁 ThreadSafeInteger m_exitedPeerCount; //加锁计数参量,每当完成一个任务自加1,初始化为0 int m_bondedPeerCount; //计算当前任务拥有多少核 int m_jobTotal; //当前需要运行的任务总数: 如在PreLookaheadGroup子类中表示当前有多少帧没有初始化(lookachead) //CostEstimateGroup子类中表示当前有多少需要计算frame-cost的帧数 1. 2. lookachead 多slice配置中:一帧有多少slice //???? int m_jobAcquired; //计数当前已经完成的任务数目 BondedTaskGroup() { m_bondedPeerCount = m_jobTotal = m_jobAcquired = 0; }//初始化 /* Do not allow the instance to be destroyed before all bonded peers have * exited processTasks() */ ~BondedTaskGroup() { waitForExit(); }//等待全部任务完成,释放内存 /* Try to enlist the help of idle worker threads on most recently associated * with the given job provider and "bond" them to work on your tasks. Up to * maxPeers worker threads will call your processTasks() method. */ /** 函数功能 : 返回当前可用核数,并在threadmain中触发相应processtask,从当前job中拥有核并且sleep状态的核才可以触发 /* 调用范围 : 只在Analysis::compressInterCU_dist、FrameEncoder::compressFrame()、Search::predInterSearch函数中被调用 * \返回 : 返回当前可用核数 * */ int tryBondPeers(JobProvider& jp, int maxPeers) { int count = jp.m_pool->tryBondPeers(maxPeers, jp.m_ownerBitmap, *this); m_bondedPeerCount += count; return count; } /* Try to enlist the help of any idle worker threads and "bond" them to work * on your tasks. Up to maxPeers worker threads will call your * processTasks() method. */ /** 函数功能 : 返回当前可用核数,并在threadmain中触发相应processtask,只要是sleep状态的核都可以触发 /* 调用范围 : 只在slicetypeDecide、CostEstimateGroup::finishBatch()、CostEstimateGroup::estimateFrameCost函数中被调用 * \返回 : 返回当前可用核数 * */ int tryBondPeers(ThreadPool& pool, int maxPeers) { int count = pool.tryBondPeers(maxPeers, ALL_POOL_THREADS, *this); m_bondedPeerCount += count; return count; } /* Returns when all bonded peers have exited processTasks(). It does *NOT* * ensure all tasks are completed (but this is generally implied). */ /** 函数功能 : 一直等待到任务全部完成,这里等待的是核释放,内核释放了任务也就完成了 /* 调用范围 : 只在compressInterCU_dist、compressFrame()、predInterSearch、slicetypeDecide()、CostEstimateGroup::finishBatch()、CostEstimateGroup::estimateFrameCost函数中被调用 * \返回 : null * */ void waitForExit() { int exited = m_exitedPeerCount.get(); while (m_bondedPeerCount != exited) //如果在threadmain释放的核数等于当前拥有的核数说明当前已经完成任务 exited = m_exitedPeerCount.waitForChange(exited); } /* Derived classes must define this method. The worker thread ID may be * used to index into thread local data, or ignored. The ID will be between * 0 and jp.m_numWorkers - 1 */ //虚函数,具体运行其子类的task virtual void processTasks(int workerThreadId) = 0;};} // end namespace x265#endif // ifndef X265_THREADPOOL_H
1 0
- x265-1.7版本-common/threadpool.h注释
- x265-1.8版本-common/threadpool.h注释
- x265-1.7版本-common/threadpool.cpp注释
- x265-1.7版本-common/bitstream.h注释
- x265-1.7版本-common/cudata.h注释
- x265-1.7版本-common/frame.h注释
- x265-1.7版本-common/framedata.h注释
- x265-1.7版本-common/lowres.h注释
- x265-1.7版本-common/picyuv.h注释
- x265-1.7版本-common/slice.h注释
- x265-1.7版本-common/threading.h注释
- x265-1.8版本-common/contexts.h注释
- x265-1.8版本-common/cudata.h注释
- x265-1.8版本-common/framedata.h注释
- x265-1.8版本-common/lowres.h注释
- x265-1.8版本-common/piclist.h注释
- x265-1.8版本-common/picyuv.h注释
- x265-1.8版本-common/predict.h注释
- 【Android】项目常用功能集锦(一)
- ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: YES)解决方法
- ListView-Arrayadapter
- 项目中使用js回显ztree使用json格式
- javaEE之------SpringMVC中ParameterMethodNameResolver应用
- x265-1.7版本-common/threadpool.h注释
- 跑的比别人久才能够赢
- HDU-1686 Oulipo
- Spring+Dubbo+MyBatis+Linner分布式Web开发环境搭建
- 即时通信系统中如何实现:聊天消息加密,让通信更安全? 【低调赠送:QQ高仿版GG 4.5 最新源码】
- XCode7,打包上传的一些警告,及参考处理方法
- 卡特兰数
- 铺地毯题解
- 【POJ 3371】 Flesch Reading Ease(模拟)