37#ifdef LOSCFG_KERNEL_VM
46 if (page == NULL || info == NULL) {
47 VM_ERR(
"UnmapPage error input null!");
63 LOS_DL_LIST_FOR_EACH_ENTRY_SAFE(info, next, immap,
LosMapInfo, node) {
219 LOS_DL_LIST_FOR_EACH_ENTRY_SAFE(fpage, fnext, activeFile,
LosFilePage, lru) {
255 LOS_DL_LIST_FOR_EACH_ENTRY_SAFE(fpage, fnext, inactive_file,
LosFilePage, lru) {
297 size_t nReclaimed = 0;
305 nPage = VM_FILEMAP_MIN_SCAN;
308 if (nPage > VM_FILEMAP_MAX_SCAN) {
309 nPage = VM_FILEMAP_MAX_SCAN;
316 if (totalPages < VM_FILEMAP_MIN_SCAN) {
322 OsShrinkActiveList(physSeg, (nPage < VM_FILEMAP_MIN_SCAN) ? VM_FILEMAP_MIN_SCAN : nPage);
328 if (nReclaimed >= nPage) {
333 LOS_DL_LIST_FOR_EACH_ENTRY_SAFE(fpage, fnext, &dirtyList,
LosFilePage, node) {
STATIC INLINE VOID LOS_AtomicDec(Atomic *v)
Atomic auto-decrement. | 对32bit原子数据做减1
LITE_OS_SEC_ALW_INLINE STATIC INLINE VOID LOS_ListTailInsert(LOS_DL_LIST *list, LOS_DL_LIST *node)
Insert a node to the tail of a doubly linked list.
LITE_OS_SEC_ALW_INLINE STATIC INLINE VOID LOS_ListDelete(LOS_DL_LIST *node)
UINT32 LOS_MemFree(VOID *pool, VOID *ptr)
释放从指定动态内存中申请的内存
UINT8 * m_aucSysMem0
异常交互动态内存池地址的起始地址,当不支持异常交互特性时,m_aucSysMem0等于m_aucSysMem1。
STATUS_T LOS_ArchMmuUnmap(LosArchMmu *archMmu, VADDR_T vaddr, size_t count)
LOS_ArchMmuUnmap 解除进程空间虚拟地址区间与物理地址区间的映射关系
VOID LOS_SpinUnlockRestore(SPIN_LOCK_S *lock, UINT32 intSave)
INT32 LOS_SpinTrylock(SPIN_LOCK_S *lock)
VOID LOS_SpinLockSave(SPIN_LOCK_S *lock, UINT32 *intSave)
VOID LOS_SpinUnlock(SPIN_LOCK_S *lock)
STATIC INLINE VOID OsSetPageActive(LosVmPage *page)
给页面贴上活动的标签
VOID OsDeletePageCacheLru(LosFilePage *page)
删除页高速缓存和LRU,对应 OsAddToPageacheLru
STATIC INLINE VOID OsCleanPageReferenced(LosVmPage *page)
给页面撕掉被引用的标签
VOID OsDoFlushDirtyPage(LosFilePage *fpage)
冲洗脏页数据,将脏页数据回写磁盘
STATIC INLINE BOOL OsIsPageMapped(LosFilePage *page)
文件页是否映射过了
STATIC INLINE BOOL OsIsPageActive(LosVmPage *page)
页面是否活动
STATIC INLINE BOOL OsIsPageDirty(LosVmPage *page)
页面是否为脏页,所谓脏页就是页内数据是否被更新过,只有脏页才会有写时拷贝
STATIC INLINE BOOL OsIsPageReferenced(LosVmPage *page)
页面是否被引用,只被一个进程引用的页叫私有页,多个进程引用就是共享页,此为共享内存的本质所在
STATIC INLINE VOID OsSetPageReferenced(LosVmPage *page)
给页面贴上被引用的标签
STATIC INLINE VOID OsCleanPageActive(LosVmPage *page)
给页面撕掉活动的标签
STATIC INLINE BOOL OsIsPageLocked(LosVmPage *page)
页面是否被锁
LosFilePage * OsDumpDirtyPage(LosFilePage *oldPage)
备份脏页,老脏页撕掉脏页标签
LOS_DL_LIST_HEAD(g_vmSpaceList)
初始化全局虚拟空间节点,所有虚拟空间都挂到此节点上.
OsLruList
Lru全称是Least Recently Used,即最近最久未使用的意思 针对匿名页和文件页各拆成对应链表。
@ VM_LRU_ACTIVE_FILE
活动文件页(磁盘)
@ VM_LRU_INACTIVE_FILE
非活动文件页(磁盘)
struct VmPhysSeg g_vmPhysSeg[VM_PHYS_SEG_MAX]
物理内存采用段页式管理,先切段后伙伴算法页
BOOL OsInactiveListIsLow(LosVmPhysSeg *physSeg)
非活动文件页低于活动文件页吗
VOID OsLruCacheAdd(LosFilePage *fpage, enum OsLruList lruType)
int OsShrinkInactiveList(LosVmPhysSeg *physSeg, int nScan, LOS_DL_LIST *list)
缩小未活动页链表
VOID OsShrinkActiveList(LosVmPhysSeg *physSeg, int nScan)
缩小活动页链表
VOID OsPageRefDecNoLock(LosFilePage *fpage)
VOID OsUnmapAllLocked(LosFilePage *page)
解除文件页在所有进程的映射
STATIC INLINE VOID OsMoveToActiveList(LosFilePage *fpage)
VOID OsLruCacheDel(LosFilePage *fpage)
STATIC INLINE VOID OsMoveToInactiveList(LosFilePage *fpage)
STATIC INLINE VOID OsMoveToActiveHead(LosFilePage *fpage)
VOID OsUnmapPageLocked(LosFilePage *page, LosMapInfo *info)
VOID OsPageRefIncLocked(LosFilePage *fpage)
int OsTryShrinkMemory(size_t nPage)
STATIC INLINE VOID OsMoveToInactiveHead(LosFilePage *fpage)
LOS_DL_LIST lru
lru节点, 结合 LosVmPhysSeg: LOS_DL_LIST lruList[VM_NR_LRU_LISTS] 理解
struct VmPage * vmPage
物理页框
struct VmPhysSeg * physSeg
struct page_mapping * mapping
此结构由文件系统提供,用于描述装入点 见于 ..\third_party\NuttX\fs\fs.h
LOS_DL_LIST node
节点,节点挂到page_mapping.page_list上,链表以 pgoff 从小到大方式排序.
虚拟地址和文件页的映射信息,在一个进程使用文件页之前,需要提前做好文件页在此内存空间的映射关系,如此通过虚拟内存就可以对文件页读写操作.
VADDR_T vaddr
虚拟地址.每个进程访问同一个文件页的虚拟地址都是不一样的
LosArchMmu * archMmu
mmu完成vaddr和page->vmPage->physAddr物理地址的映射
LOS_DL_LIST node
节点,挂到page->i_mmap链表上.链表上记录要操作文件页的进程对这个page的映射信息
物理页框描述符 虚拟内存体现的是程序对内存资源的需求,而物理内存是对该请求的供应。 伙伴算法的思想是:把内存中连续的空闲页框空间看成是空闲页框块,并按照它们的大小(连续页框的数目)分组
LOS_DL_LIST lruList[VM_NR_LRU_LISTS]
页面置换算法,5个双循环链表头,它们分别描述五中不同类型的链表
SPIN_LOCK_S lruLock
用于置换的自旋锁,用于操作lruList
size_t lruSize[VM_NR_LRU_LISTS]
5个双循环链表大小,如此方便得到size