Linux内存模型之bootmem分配器二

**********************************

*  在arch/arm/kernel/setup.c中,
*  sanity_check_meminfo();

**********************************
arm_memblock_init(&meminfo, mdesc);

arch/arm/mm中,
void __init sanity_check_meminfo(void)
{
 int i, j, highmem = 0;

        //遍历所有的bank
 for (i = 0, j = 0; i < meminfo.nr_banks; i++) {
  struct membank *bank = &meminfo.bank[j];
  *bank = meminfo.bank[i];

#ifdef CONFIG_HIGHMEM
       //如果定义了高端内存,地址范围在高端内,则标记
  if (__va(bank->start) >= vmalloc_min ||
      __va(bank->start) < (void *)PAGE_OFFSET)
   highmem = 1;

  bank->highmem = highmem;       //标记

  /*
   * Split those memory banks which are partially overlapping
   * the vmalloc area greatly simplifying things later.
   */
                //范围在低端内存,但是size大于低端范围也就是
                //起始地址在低端,结束地址超过低端范围
  if (__va(bank->start) < vmalloc_min &&
      bank->size > vmalloc_min - __va(bank->start)) {
                        //banks号大于等于总数量,则直接忽略该bank
                        //否则将该bank分成两个bank,高端部分标记成高端
   if (meminfo.nr_banks >= NR_BANKS) {
    printk(KERN_CRIT "NR_BANKS too low, "
       "ignoring high memory\n");
   } else {
    memmove(bank + 1, bank,
     (meminfo.nr_banks - i) * sizeof(*bank));
    meminfo.nr_banks++;
    i++;
    bank[1].size -= vmalloc_min - __va(bank->start);
    bank[1].start = __pa(vmalloc_min - 1) + 1;
    bank[1].highmem = highmem = 1;
    j++;
   }
   bank->size = vmalloc_min - __va(bank->start);
  }
#else
  bank->highmem = highmem;   //没定义就赋值为0

  /*
   * Check whether this memory bank would entirely overlap
   * the vmalloc area.
   */
                //没定义高端地址,那么高端部分全部忽略
  if (__va(bank->start) >= vmalloc_min ||
      __va(bank->start) < (void *)PAGE_OFFSET) {
   printk(KERN_NOTICE "Ignoring RAM at %.8llx-%.8llx "
          "(vmalloc region overlap).\n",
          (unsigned long long)bank->start,
          (unsigned long long)bank->start + bank->size - 1);
   continue;
  }

  /*
   * Check whether this memory bank would partially overlap
   * the vmalloc area.
   */
  if (__va(bank->start + bank->size) > vmalloc_min ||
      __va(bank->start + bank->size) < __va(bank->start)) {
   unsigned long newsize = vmalloc_min - __va(bank->start);
   printk(KERN_NOTICE "Truncating RAM at %.8llx-%.8llx "
          "to -%.8llx (vmalloc region overlap).\n",
          (unsigned long long)bank->start,
          (unsigned long long)bank->start + bank->size - 1,
          (unsigned long long)bank->start + newsize - 1);
   bank->size = newsize;
  }
#endif
  if (!bank->highmem && bank->start + bank->size > lowmem_limit)
   lowmem_limit = bank->start + bank->size;

  j++;
 }
#ifdef CONFIG_HIGHMEM
        //如果是高端内存,还要进行进一步支持的确认,vipt的不支持
 if (highmem) {
  const char *reason = NULL;

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/22652.html