1.常见数据结构
1)io请求结构,对stub的简单封装,将stub组织成双向队列
structiot_request{
structlist_headlist;/*将io请求加入链表*/
call_stub_t*stub;
};
2)工作者结构,负责为请求服务
structiot_worker{
structlist_headrqlist;/*分派给我的io请求链表*/
structiot_conf*conf;
int64_tq,dq;
pthread_cond_tdq_cond;
pthread_mutex_tqlock;
int32_tqueue_size;
pthread_tthread;
intstate;/*线程所处状态.*/
intthread_idx;
/*Thread'hiswillbethread
localdata,forensuringthat
numberofthreadsdontfallbelow
aminimum,wejustdontallow
threadswithspecificindicesto
sineliminatingone
placewhereotherwialock
wouldhavebeenrequiredtoupdate
centralizedstateinsideconf.*/
};
structiot_conf{
int32_tthread_count;
structiot_worker**workers;
xlator_t*this;
/*Configstatefororderedthreads.*/
pthread_mutex_totlock;/*Udtosyncanystatethatneeds
tobechangedbytheordered
threads.
*/
intmax_o_threads;
/*已排序(ordered)线程的最大数目*/
intmin_o_threads;
/*已排序线程的最小值,已排序线程的数目永远不低于这个数目*/
into_idle_time;
/*以秒为单位,某已排序线程退出后的空闲时间*/
gf_boolean_to_scaling;
/*如果用户不想动态增减线程数目,则设置为IOT_SCALING_OFF。此时,
io-threads维护维护min_o_threads个线程,且不允许任何线程退出*/
structiot_worker**oworkers;/*已排序线程池.*/
/*为未排序线程进行配置*/
pthread_mutex_tutlock;/*Udforscalingun-ordered
threads.*/
structiot_worker**uworkers;/*Un-orderedthreadpool.*/
intmax_u_threads;/*Numberofunorderedthreads
will
notbehigherthanthis.*/
intmin_u_threads;/*Numberofunorderedthreads
shouldnotfallbelowthis
value.
*/
intu_idle_time;/*Ifanunorderedthreaddoesnot
getarequestforthis
amountof
cs,itshouldtrytodie.
*/
gf_boolean_tu_scaling;/*SettoIOT_SCALING_OFFif
ur
doesnotwantthread
scalingon
scalingis
off,io-threadsmaintainsat
leastmin_u_threads
numberof
threadsandneverletsany
thread
exit.
*/
pthread_attr_tw_attr;
/*用来减小堆栈的大小,相对于默认的8MB来说
Worker的工作线程会用到这个线程属性*/
};
对于调度函数的疑问:为什么已排序请求调度函数需要对inode上锁以后才调度,
而未排序请求调度函数不需要?
1.未排序请求调度函数分析
该函数首先以自己收到得conf作为参数调用未排序请求平衡器函数获取一个索
引,然后用该索引从conf得uworker中选取一个工作者,对stub封装成请求,
然后调用点火线程,确保线程开始运行。
在平衡器函数中,调用随机数生成函数生成一个随机数,然后根据是否配置了伸
缩性对次随机数求余,反悔一个合法得索引。这种随即调度的方法没有考虑到当
前负载的平衡性,具体来说没有分析每个uworker得请求队列长度,可能造成负
载得不平衡,所以对其进行改进,改进的时候需要检测每个uworker的队列长度。
所以要分析在初始化的时候是不是每个worker的队列长度都初始化了,因此要
查阅初始化部分代码。
经过查找,在allocate_worker_array函数内部为worker分配空间的时候调用的是
calloc函数,所以结构内各成员都被清0,因此在平衡器中可安全访问。
2.已排序请求调度函数分析
此函数比未排序请求调度函数要复杂一些,在调度之前先要上上锁,然后调
用已排序请求平衡器函数,该平衡器函数和未排序平衡器在参数和返回值是
行均不同,如果返回负数表示处所,此时调度函数返回。
在已排序平衡器函数中可以看到,该函数先去inode的ctx中找,看是否存在
该conf中的xlator对应的索引,如果有则取出来;如果没有则调用
iot_create_inode_worker_assoc创建一个并加入到ctx中,所以对已排序请求
的真正调度发生在iot_create_inode_worker_assoc函数中,跳入次函数可以看
到这里仍然采用的是生成随机数的方法,特对此加以改进
本文发布于:2023-01-04 06:11:13,感谢您对本站的认可!
本文链接:http://www.wtabcd.cn/fanwen/fan/90/89091.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
留言与评论(共有 0 条评论) |