linux fd类型6,Linux内核中的文件描述符(六)--fd的分配--expand_files

Kernel version:2.6.14

CPU architecture:ARM920T

我们先贴出expand_files函数的源码:

int expand_files(struct files_struct *files, int nr)

{

int err, expand = 0;

struct fdtable *fdt;

fdt = files_fdtable(files);

if (nr >= fdt->max_fdset || nr >= fdt->max_fds) {  //我们在前面的文章中已经分析过,初始时max_fdset = 1024,max_fds = 32

if (fdt->max_fdset >= NR_OPEN ||  //#define NR_OPEN (1024*1024) /* Absolute upper limit on fd num */

fdt->max_fds >= NR_OPEN || nr >= NR_OPEN) {

err = -EMFILE;  //max_fdset和max_fds都不能大于 NR_OPEN,否则返回 -EMFILE,即打开太多的文件

goto out;

}

expand = 1;

if ((err = expand_fdtable(files, nr)))//真正进行扩展

goto out;

}

err = expand;

out:

return err;

}

expand_files函数进行一些检查后调用expand_fdtable进行文件描述符表的扩展,下面分析expand_fdtable函数。

static int expand_fdtable(struct files_struct *files, int nr)

__releases(files->file_lock)

__acquires(files->file_lock)

{

int error = 0;

struct fdtable *fdt;

struct fdtable *nfdt = NULL;

spin_unlock(&files->file_lock);

nfdt = alloc_fdtable(nr);//根据nr重新创建一个新的fdtable

if (!nfdt) {

error = -ENOMEM;

spin_lock(&files->file_lock);

goto out;

}

spin_lock(&files->file_lock);

fdt = files_fdtable(files);

/*

* Check again since another task may have expanded the

* fd table while we dropped the lock

*/

if (nr >= fdt->max_fds || nr >= fdt->max_fdset) { //nr值必须大于max_fds和max_fdset值,这里再次进行检查是防止另一个进程进行了expand

copy_fdtable(nfdt, fdt); //将旧的fdtable中的内容拷贝至新的fdtable

} else {

/* Somebody expanded while we dropped file_lock */

spin_unlock(&files->file_lock);

__free_fdtable(nfdt);

spin_lock(&files->file_lock);

goto out;

}

rcu_assign_pointer(files->fdt, nfdt);//用新的fdtable替换旧的fdtable  

free_fdtable(fdt);//释放旧的fdtable 

out:

return error;

}0b1331709591d260c1c78e86d0c51c18.png

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值