本文共 2156 字,大约阅读时间需要 7 分钟。
numabalance的本意是让进程和其使用的memory在同一个numa节点上,这样延迟最小。但是这需要调动器来做大量的工作来迁移进程和memory到同一个node上,这样对某些场景性能会有比较大的损耗。一般debug时候如果perf top中看到迁移进程的函数则建议观点numabalance试试numabalance迁移的过程如下:在每个时钟中断update_process_times->scheduler_tickvoid scheduler_tick(void){ #这个函数会调用调度器的定义的hook函数,以fair 调度为例 curr->sched_class->task_tick(rq, curr, 0); }static void task_tick_fair(struct rq *rq, struct task_struct *curr, int queued){ struct cfs_rq *cfs_rq; struct sched_entity *se = &curr->se; #调度器选择下一个要执行的函数 for_each_sched_entity(se) { cfs_rq = cfs_rq_of(se); entity_tick(cfs_rq, se, queued); }#只有开了numabalance这个if条件才会成立,可见只有开了numabalance才会迁移进程和memory到同一个node上 if (static_branch_unlikely(&sched_numa_balancing)) task_tick_numa(rq, curr);}void task_tick_numa(struct rq *rq, struct task_struct *curr){ if (now > curr->node_stamp + period) { if (!curr->node_stamp) curr->numa_scan_period = task_scan_start(curr); curr->node_stamp += period;#这里每个jiffies扫描一次,这里添加一个work,其回调函数是task_numa_work,这个函数最主要的工作就是调用change_prot_numa把#所有映射到VMA的PTE页表项该为PAGE_NONE if (!time_before(jiffies, curr->mm->numa_next_scan)) { init_task_work(work, task_numa_work); /* TODO: move this into sched_fork() */ task_work_add(curr, work, true); } }}这样改的目的是当下次访问这个页时就会发生缺页中断,这样我们就可以在缺页中断中迁移进程和其使用的页static int handle_pte_fault(struct vm_fault *vmf){#由于我们在中断中我们把页的pte改成none了,一次下面这个if条件会成立 if (pte_protnone(vmf->orig_pte) && vma_is_accessible(vmf->vma)) return do_numa_page(vmf);}static int do_numa_page(struct vm_fault *vmf){ last_cpupid = page_cpupid_last(page); page_nid = page_to_nid(page); #需要迁移目的node id target_nid。如果target_nid等于-1,则表示页就在自己的numa节点上不用迁移 target_nid = numa_migrate_prep(page, vma, vmf->address, page_nid, &flags); pte_unmap_unlock(vmf->pte, vmf->ptl); if (target_nid == -1) { put_page(page); goto out; } /* Migrate to the requested node */ #通过下面函数将页迁移到自己分配的numa 节点上 migrated = migrate_misplaced_page(page, vma, target_nid); if (migrated) { page_nid = target_nid; flags |= TNF_MIGRATED; } else flags |= TNF_MIGRATE_FAIL;out:#页面迁移完成后,再通过task_numa_fault 来迁移task if (page_nid != -1) task_numa_fault(last_cpupid, page_nid, 1, flags); return 0;}从整个过程看numa balance 会做额外很大工作,因此某些场景下严重影响性能,需要关掉.
转载地址:http://ljnmi.baihongyu.com/