进程创建时IO处理

 

static int copy_io(unsigned long clone_flags, struct task_struct *tsk) { #ifdef CONFIG_BLOCK  struct io_context *ioc = current->io_context;  struct io_context *new_ioc;

 if (!ioc)   return 0;  /*   * Share io context with parent, if CLONE_IO is set   */  if (clone_flags & CLONE_IO) {   ioc_task_link(ioc);   tsk->io_context = ioc;  } else if (ioprio_valid(ioc->ioprio)) {   new_ioc = get_task_io_context(tsk, GFP_KERNEL, NUMA_NO_NODE);   if (unlikely(!new_ioc))    return -ENOMEM;

  new_ioc->ioprio = ioc->ioprio;   put_io_context(new_ioc);  } #endif  return 0; }

/**  * get_task_io_context - get io_context of a task  * @task: task of interest  * @gfp_flags: allocation flags, used if allocation is necessary  * @node: allocation node, used if allocation is necessary  *  * Return io_context of @task.  If it doesn't exist, it is created with  * @gfp_flags and @node.  The returned io_context has its reference count  * incremented.  *  * This function always goes through task_lock() and it's better to use  * %current->io_context + get_io_context() for %current.  */ struct io_context *get_task_io_context(struct task_struct *task,            gfp_t gfp_flags, int node) {  struct io_context *ioc;

 might_sleep_if(gfpflags_allow_blocking(gfp_flags));

 do {   task_lock(task);   ioc = task->io_context;   if (likely(ioc)) {    get_io_context(ioc);    task_unlock(task);    return ioc;   }   task_unlock(task);  } while (!create_task_io_context(task, gfp_flags, node));

 return NULL; }

int create_task_io_context(struct task_struct *task, gfp_t gfp_flags, int node) {  struct io_context *ioc;  int ret;

 ioc = kmem_cache_alloc_node(iocontext_cachep, gfp_flags | __GFP_ZERO,         node);  if (unlikely(!ioc))   return -ENOMEM;

 /* initialize */  atomic_long_set(&ioc->refcount, 1);  atomic_set(&ioc->nr_tasks, 1);  atomic_set(&ioc->active_ref, 1);  spin_lock_init(&ioc->lock);  INIT_RADIX_TREE(&ioc->icq_tree, GFP_ATOMIC | __GFP_HIGH);  INIT_HLIST_HEAD(&ioc->icq_list);  INIT_WORK(&ioc->release_work, ioc_release_fn);

 /*   * Try to install.  ioc shouldn't be installed if someone else   * already did or @task, which isn't %current, is exiting.  Note   * that we need to allow ioc creation on exiting %current as exit   * path may issue IOs from e.g. exit_files().  The exit path is   * responsible for not issuing IO after exit_io_context().   */  task_lock(task);  if (!task->io_context &&      (task == current || !(task->flags & PF_EXITING)))   task->io_context = ioc;  else   kmem_cache_free(iocontext_cachep, ioc);

 ret = task->io_context ? 0 : -EBUSY;

 task_unlock(task);

 return ret; }

 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值