您的位置 首页 报告

linux内核中的文件描述符(四)–fd的分配–get_unused_fd

Kernelversion:2614CPUarchitecture:ARM920TAuthor:ce123(http:blogcsdnnetce123)在linux内核中主要有两个函数涉及到文件描

Kernel version:2.6.14

CPU architecture:ARM920T

Author:ce123(http://blog.csdn.net/ce123)

linux内核中首要有两个函数涉及到文件描述符的分配:get_unused_fd和locate_fd。本文首要解说get_unused_fd,将会鄙人一篇文章中介绍locate_fd。首要给出get_unused_fd的界说(fs/open.c):

[plain]view plaincopy

print?

  1. intget_unused_fd(void)
  2. {
  3. structfiles_struct*files=current->files;//取得当时进程的翻开文件列表files
  4. intfd,error;
  5. structfdtable*fdt;
  6. error=-EMFILE;
  7. spin_lock(&files->file_lock);
  8. repeat:
  9. fdt=files_fdtable(files);//取得文件描述符位图结构
  10. fd=find_next_zero_bit(fdt->open_fds->fds_bits,
  11. fdt->max_fdset,
  12. fdt->next_fd);
  13. //find_next_zero_bit函数在文件描述符位图fds_bits中从next_fd位开端查找下一个(包含next_fd)为0的位,也便是分配一个文教描述符
  14. /*
  15. *N.B.Forclonetaskssharingafilesstructure,thistest
  16. *willlimitthetotalnumberoffilesthatcanbeopened.
  17. */
  18. if(fd>=current->signal->rlim[RLIMIT_NOFILE].rlim_cur)//查看是否超越当时进程限制的最大可翻开文件数
  19. gotoout;
  20. /*Doweneedtoexpandthefdarrayorfdset?*/
  21. error=expand_files(files,fd);//根据需要扩展fd,稍后咱们会具体介绍该函数。返回值<0,过错;返回值>0,扩展后再次进行fd的分配
  22. if(error<0)
  23. gotoout;
  24. if(error){
  25. /*
  26. *Ifweneededtoexpandthefsarraywe
  27. *mighthaveblocked-tryagain.
  28. */
  29. error=-EMFILE;
  30. gotorepeat;//之前进行了扩展操作,从头进行一次闲暇fd的分配
  31. }
  32. FD_SET(fd,fdt->open_fds);//在open_fds的位图上置位
  33. FD_CLR(fd,fdt->close_on_exec);
  34. fdt->next_fd=fd+1;//next_fd加1
  35. #if1
  36. /*Sanitycheck*/
  37. if(fdt->fd[fd]!=NULL){
  38. printk(KERN_WARNING”get_unused_fd:slot%dnotNULL!\n”,fd);
  39. fdt->fd[fd]=NULL;
  40. }
  41. #endif
  42. error=fd;
  43. out:
  44. spin_unlock(&files->file_lock);
  45. returnerror;
  46. }

current->signal->rlim[RLIMIT_NOFILE].rlim_cur是一个进程能够翻开的最大文件数量。咱们首要来看RLIMIT_NOFILE,该值界说如下:

[plain]view plaincopy

print?

  1. #defineRLIMIT_NOFILE7/*maxnumberofopenfiles*/

在signal结构中,rlim是struct rlimit类型的数组,

[plain]view plaincopy

print?

  1. structsignal_struct{
  2. structrlimitrlim[RLIM_NLIMITS];
  3. };

struct rlimit界说如下

[plain]view plaincopy

print?

  1. structrlimit{
  2. unsignedlongrlim_cur;//当时值
  3. unsignedlongrlim_max;//最大值
  4. };

这些值时是在哪设定的呢?咱们应该知道,linux内核经过fork创立进程,第一个进程是静态界说的。因而,假如进程创立后没有修正这些值,那么这些和第一个进程中的值应该是相同的。下面是第一个进程的task_struct结构,仅列出部分数据。

[plain]view plaincopy

print?

  1. linux/arch/arm/kernel/init_task.c
  2. structtask_structinit_task=INIT_TASK(init_task);
  3. #defineINIT_TASK(tsk)\
  4. {\
  5. .signal=&init_signals,\
  6. }

init_signals的界说如下:

[plain]view plaincopy

print?

  1. #defineINIT_SIGNALS(sig){\
  2. .count=ATOMIC_INIT(1),\
  3. .wait_chldexit=__WAIT_QUEUE_HEAD_INITIALIZER(sig.wait_chldexit),\
  4. .shared_pending={\
  5. .list=LIST_HEAD_INIT(sig.shared_pending.list),\
  6. .signal={{0}}},\
  7. .posix_timers=LIST_HEAD_INIT(sig.posix_timers),\
  8. .cpu_timers=INIT_CPU_TIMERS(sig.cpu_timers),\
  9. .rlim=INIT_RLIMITS,\
  10. }
  11. include\asm-generic\resource.h
  12. #defineINIT_RLIMITS\
  13. {\
  14. [RLIMIT_CPU]={RLIM_INFINITY,RLIM_INFINITY},\
  15. [RLIMIT_FSIZE]={RLIM_INFINITY,RLIM_INFINITY},\
  16. [RLIMIT_DATA]={RLIM_INFINITY,RLIM_INFINITY},\
  17. [RLIMIT_STACK]={_STK_LIM,_STK_LIM_MAX},\
  18. [RLIMIT_CORE]={0,RLIM_INFINITY},\
  19. [RLIMIT_RSS]={RLIM_INFINITY,RLIM_INFINITY},\
  20. [RLIMIT_NPROC]={0,0},\
  21. [RLIMIT_NOFILE]={INR_OPEN,INR_OPEN},\
  22. [RLIMIT_MEMLOCK]={MLOCK_LIMIT,MLOCK_LIMIT},\
  23. [RLIMIT_AS]={RLIM_INFINITY,RLIM_INFINITY},\
  24. [RLIMIT_LOCKS]={RLIM_INFINITY,RLIM_INFINITY},\
  25. [RLIMIT_SIGPENDING]={0,0},\
  26. [RLIMIT_MSGQUEUE]={MQ_BYTES_MAX,MQ_BYTES_MAX},\
  27. [RLIMIT_NICE]={0,0},\
  28. [RLIMIT_RTPRIO]={0,0},\
  29. }
  30. #defineNR_OPEN(1024*1024)/*Absoluteupperlimitonfdnum*/
  31. #defineINR_OPEN1024/*Initialsettingfornfilerlimits*/

从上面的代码咱们能够看到rlim_cur = 1024,也便是说进程最多能够翻开1024个文件。

声明:本文内容来自网络转载或用户投稿,文章版权归原作者和原出处所有。文中观点,不代表本站立场。若有侵权请联系本站删除(kf@86ic.com)https://www.86ic.net/ceping/baogao/262410.html

为您推荐

联系我们

联系我们

在线咨询: QQ交谈

邮箱: kf@86ic.com

关注微信
微信扫一扫关注我们

微信扫一扫关注我们

返回顶部