1.DMA 和 cache 一致性
(1) 不带 CACHE
自己写驱动,申请 DMA,可以用 Coherent DMA buffers
void * dma_alloc_coherent(struct device *dev, size_t size, dma_addr_t
*dma_handle,gfp_t flag);
void dma_free_coherent (struct device *dev, size_t size,void *cpu_addr,
dma_addr_t dma_handle);
CMA 和此 API 自动融合,调用 dma_alloc_coherent() 将从 CMA 获得内存,不带 cache。
(2) 流式 DMA:
操作其他进程的地址,比如 tcp/ip 报文的缓存,无法控制 DMA 地址源,
用 dma_map_single,自动设置 cache flush,
CPU 无法访问 cache,这个是硬件自动完成的;但是 CPU 可以控制 cache,使能 cache 为非法 (破坏命中),会自动与 memory 同步。
DMA Streaming Mapping
dma_addr_t dma_map_single(...);
void dma_unmap_single (...);
有的强大 DMA,不需要连续内存做 DMA 操作,scater/getter 可以用
int dma_map_sg(...);
void dma_unmap_sg (...);
有一些强大硬件,DMA 能感知 cache 网络互联;
这 3 套 API,对任何硬件都成立;实现 API 后端,兼容不同硬件。
有些新的强大硬件,有支持 IOMMU/smmu
Dma 可以从不连续内存,CMA 申请内存
dma_alloc_coherent 不需要从 CMA 申请内存,支持 MMU,可以用物理不连续的内存来实现 DMA 操作;
2. 内存的 cgroup
./swapoff –a
echo 1 \> /proc/sys/vm/overcommit_memory //
/sys/fs/cgroup/memory
mkdir A
cd A
sudo echo \$(100\*1024\*1024) \> memory.limit_in_bytes // 限制最大内存 100M
//a.out 放到 A cgroup 执行;sudo cgexec –g memory:A ./a.out
3. 性能方面的调优:page in/out, swapin/out
4. Dirty ratio 的一些设置
脏页写回
时间维度 :时间到,脏页写回;dirty_expire_centisecs
空间维度 :Dirty_ratio
Dirty_background_ratio:
cd /proc/sys/vm
假如某个进程在不停写数据,当写入大小触发 dirty_background_ratio_10% 时,脏页开始写入磁盘,写入数据大小触发 dirty_ratio_20% 时 (磁盘 IO 速度远比写内存慢),如果继续写,会被内核阻塞,等脏页部分被写入磁盘,释放 pagecached 后,进程才能继续写入内存;
所有的脏页 flush,都是后台自动完成,当写入速度不足以触发 dirty_ratio 时,进程感知不到磁盘的存在。
5. swappiness
内存回收 reclaim,涉及三个水位,
回收哪里的内存,back_groudpages, swap,由 swappiness 决定
Swappiness 越大,越倾向于回收匿名页;
即使 Swappiness 设置为 0,先回收背景页,以使达到最低水位;假使达不到,还是会回收匿名页;
有个例外 ,对于 cgroup 而言,设置 swappiness=0,该 group 的 swap 回收被关闭;但是全局的 swap 还是可以回收;
为什么设定最低水位,在 Linux 有一些紧急申请,PF_MEMALLOC,可以突破 min 水位,(回收内存的过程,也需要申请内存,类似征粮队自身需要吃粮食)。
最低水位,可以通过 lewmem_reserve_ratio 修改;
关于最低水位的计算方法:
回收 inode/dentry 的 slab
设置 drop_caches
getdelays 工具
getdelays 测量调度、I/O、SWAP、Reclaim 的延迟,需要内核打开相应选项
CONFIG_TASK_DELAY_ACCT=y
CONFIG_TASKSTATS=y
Documentation/accounting/delay-accounting.txt
vmstat
用法,man vmstate
模糊查找
apropos timer
(base) leon\@pc:\~/work/myHub/linux/kernel/linux/Documentation/accounting\$
apropos vmstat
vmstat (8) - Report virtual memory statistics
(base) leon\@pc:\~/work/myHub/linux/kernel/linux/Documentation/accounting\$
6. 其他文章
宋宝华《关于 DMA 和 dma_alloc_coherent 若干误解的澄清》