Arm64 linux Virtual memory分析

本文详细介绍了ARM32和ARM64架构的内存布局,包括用户和内核地址空间的划分。在ARM32中,内核通过线性映射和remap利用全部4G空间,而用户空间仅使用3G。ARM64则拥有更大的48位虚拟地址空间。文章还探讨了虚拟地址的建立,如通过mmap函数进行映射和munmap解除映射,并展示了文件映射的基本流程。此外,还提到了vm_area_struct在进程中的作用以及如何遍历vma。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Memory layout

ARM32 memory layout

 

ARM32 虚拟地址设定:

  1. 用户地址空间: 0~3G
  2. 内核地址空间:3G+16M ~ 4G

内核的虚拟地址只有 1G空间,对于需要访问4G 范围地址是不够的,因此对于内核而言,kmalloc, vmalloc 建立ZONE_DMA, ZONE_NORMAL 的线性映射,而对于剩下的部分,内核需要时 remap 到ZONE_HIGHMEM, 用完释放掉以便其它模块复用,从而利用4G 空间。

用户空间,则实际只访问了3G 空间,它映射到 ZONE_HIGNMEM 物理地址空间。

ARM64 memory layout

 

ARM64 的虚拟地址足够大,通常使用 48bit 来描述地址范围

用户地址:0x0000 0000 0000 0000 0000 0000 0000 0000 ~ 0x0000 7fff ffff ffff ffff ffff ffff ffff

内核地址:0xffff 8000 0000 0000 0000 0000 0000 0000 ~ 0xffff ffff ffff ffff ffff ffff ffff ffff

如果地址落在上面两个范围之外,则说明地址异常。

虚拟地址描述

加载ELF 创建 vm_area_struct

 对于一个进程,其虚拟地址的 vma ,如 stack, heap, data, bin 等都是在 load elf binary 过程中加载实现的,对于 stack, heap, bss 这些是通过 map anonymous memory 建立 vma, 而对于 data,text 则主要是 map file 实现的。

vm_area_struct 在进程中描述

 

Linux 对于每个线程,它用 task_struct 来进行描述,对于除了 Kthread的线程之外,都有一个 mm_struct, 它描述进程的虚拟内存空间,对于虚拟地址中的每个部分,都使用一个结构体 struct vm_area_struct 来描述。

在进程中, vm_area_struct 彼此之间通过双向链表关联起来,同时在 mm_struct 中 mm_rb用来快速查找一个 vma.

  • 遍历 vma 方式
static void dump_task_vma(struct task_struct *tsk)
{
   struct mm_struct *mm = tsk->mm;
   struct vm_area_struct *vma;
   unsigned long flags;
   char perm[BUFLEN] = {0};
   int count;                                                                                                       

   for (vma = mm->mmap; vma; vma = vma->vm_next) {
   
   }

mmap

函数

void *mmap(void *addr, size_t length, int prot, int flags,
                  int fd, off_t offset);
                  
int munmap(void *addr, size_t length);

建立函数的映射和解除映射。

对于映射,其参数解释:

  1. Addr: 映射地址
  2. Length: 映射内存长度
  3. Prot: 映射内存属性
  4. Flags: 映射的 map shared 还是 map private
  5. Fd: 映射的文件
  6. Offset: 映射的文件的偏移,anonymous 映射时一般为0

映射示意

 

对于文件映射,其基本流程是:

  1. File 读到 dram 作为 page cache
  2. 通过 mmu 建立 physical address 和 virtual address 的映射
  3. 用户通过指针即可对文件进行读写操作

对于mmap 本身而言,read/write 是需要用户自己进行并发控制的。

映射时序

建立映射基本要点:

  1. 通过 mmap 传递的 fd, offset, length, prot, flags 等参数,在 virtual memory area 中找到一个 gap 满足需求的地址范围
  2. 使用 vm_area_alloc 分配一个 vma
  3. 将 vma 添加到 rbtree 中去

Vma 如何分配 page?

Pagefault 映射

这里仅从宏观上分析vma 的page建立方式, 关于pgfault 具体细节分析,我们下次继续。

 

### Erlang on ARM64 Architecture Installation Configuration Compatibility For the installation, configuration, and compatibility of Erlang on the ARM64 architecture, several considerations are important to ensure a smooth setup process. #### Prerequisites for Installing Erlang on ARM64 Before installing Erlang on an ARM64 system, it's essential that certain dependencies and tools be available. These include build essentials like `gcc`, `make`, and other libraries required by OTP (Open Telecom Platform). On many Linux distributions targeting ARM64 such as Ubuntu or Debian-based systems, these can typically be installed using package managers: ```bash sudo apt-get update && sudo apt-get install -y build-essential libncurses5-dev openssl libssl-dev fop xsltproc unixodbc-dev ``` This ensures all necessary components are present for compiling from source if needed[^1]. #### Obtaining Erlang Binaries Compatible with ARM64 Official precompiled binaries specifically tailored for ARM64 may not always exist directly through conventional channels due to less frequent updates compared to mainstream architectures like x86_64. However, community-supported repositories often provide up-to-date versions suitable for this hardware type. One approach involves fetching packages via third-party sources known for supporting multiple platforms including ARM64 processors. Alternatively, building Erlang from its official GitHub repository allows customization according to specific requirements while ensuring full support across different CPU types: ```bash git clone https://github.com/erlang/otp.git otp_src cd otp_src ./bootstrap ./configure --enable-bootstrap-only --with-ssl=/usr/include/openssl make -j$(nproc) sudo make install ``` The above commands facilitate downloading, configuring, making, and finally installing Erlang onto your machine running under ARM64 instruction set[^2]. #### Configuring Erlang Environment Post-installation After successful installation either through binary downloads or compilation processes mentioned earlier, setting environment variables becomes crucial so applications know where executables reside within filesystem paths. Adding lines similar below into shell profile files (`~/.bashrc` or equivalent depending upon terminal emulator used): ```bash export PATH=$PATH:/usr/local/lib/erlang/bin export MANPATH=$MANPATH:/usr/local/lib/erlang/man ``` These adjustments help integrate newly added software seamlessly without requiring manual specification every time invocation occurs during development activities involving BEAM virtual machines hosted over ARM64 silicon chips[^3]. --related questions-- 1. What challenges might one face when porting existing Erlang codebases intended originally for X86 architectures towards newer ARM processor families? 2. How does performance compare between native ARM64 compiled Erlang programs versus those executed inside emulation layers designed primarily around older generations' CPUs? 3. Are there any notable differences in memory management techniques employed internally by the BEAM VM optimized explicitly for ARM SoCs rather than traditional desktop/server-grade alternatives based on Intel/AMD designs?
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值