LCOV - code coverage report
Current view: top level - fs/proc - task_mmu.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 244 367 66.5 %
Date: 2014-02-18 Functions: 27 30 90.0 %
Branches: 142 241 58.9 %

           Branch data     Line data    Source code
       1                 :            : #include <linux/mm.h>
       2                 :            : #include <linux/hugetlb.h>
       3                 :            : #include <linux/huge_mm.h>
       4                 :            : #include <linux/mount.h>
       5                 :            : #include <linux/seq_file.h>
       6                 :            : #include <linux/highmem.h>
       7                 :            : #include <linux/ptrace.h>
       8                 :            : #include <linux/slab.h>
       9                 :            : #include <linux/pagemap.h>
      10                 :            : #include <linux/mempolicy.h>
      11                 :            : #include <linux/rmap.h>
      12                 :            : #include <linux/swap.h>
      13                 :            : #include <linux/swapops.h>
      14                 :            : #include <linux/mmu_notifier.h>
      15                 :            : 
      16                 :            : #include <asm/elf.h>
      17                 :            : #include <asm/uaccess.h>
      18                 :            : #include <asm/tlbflush.h>
      19                 :            : #include "internal.h"
      20                 :            : 
      21                 :          0 : void task_mem(struct seq_file *m, struct mm_struct *mm)
      22                 :            : {
      23                 :            :         unsigned long data, text, lib, swap;
      24                 :            :         unsigned long hiwater_vm, total_vm, hiwater_rss, total_rss;
      25                 :            : 
      26                 :            :         /*
      27                 :            :          * Note: to minimize their overhead, mm maintains hiwater_vm and
      28                 :            :          * hiwater_rss only when about to *lower* total_vm or rss.  Any
      29                 :            :          * collector of these hiwater stats must therefore get total_vm
      30                 :            :          * and rss too, which will usually be the higher.  Barriers? not
      31                 :            :          * worth the effort, such snapshots can always be inconsistent.
      32                 :            :          */
      33                 :       4363 :         hiwater_vm = total_vm = mm->total_vm;
      34         [ +  + ]:       4363 :         if (hiwater_vm < mm->hiwater_vm)
      35                 :            :                 hiwater_vm = mm->hiwater_vm;
      36                 :            :         hiwater_rss = total_rss = get_mm_rss(mm);
      37         [ #  # ]:       4363 :         if (hiwater_rss < mm->hiwater_rss)
      38                 :            :                 hiwater_rss = mm->hiwater_rss;
      39                 :            : 
      40                 :          0 :         data = mm->total_vm - mm->shared_vm - mm->stack_vm;
      41                 :          0 :         text = (PAGE_ALIGN(mm->end_code) - (mm->start_code & PAGE_MASK)) >> 10;
      42                 :          0 :         lib = (mm->exec_vm << (PAGE_SHIFT-10)) - text;
      43                 :            :         swap = get_mm_counter(mm, MM_SWAPENTS);
      44                 :          0 :         seq_printf(m,
      45                 :            :                 "VmPeak:\t%8lu kB\n"
      46                 :            :                 "VmSize:\t%8lu kB\n"
      47                 :            :                 "VmLck:\t%8lu kB\n"
      48                 :            :                 "VmPin:\t%8lu kB\n"
      49                 :            :                 "VmHWM:\t%8lu kB\n"
      50                 :            :                 "VmRSS:\t%8lu kB\n"
      51                 :            :                 "VmData:\t%8lu kB\n"
      52                 :            :                 "VmStk:\t%8lu kB\n"
      53                 :            :                 "VmExe:\t%8lu kB\n"
      54                 :            :                 "VmLib:\t%8lu kB\n"
      55                 :            :                 "VmPTE:\t%8lu kB\n"
      56                 :            :                 "VmSwap:\t%8lu kB\n",
      57                 :            :                 hiwater_vm << (PAGE_SHIFT-10),
      58                 :            :                 total_vm << (PAGE_SHIFT-10),
      59                 :          0 :                 mm->locked_vm << (PAGE_SHIFT-10),
      60                 :          0 :                 mm->pinned_vm << (PAGE_SHIFT-10),
      61                 :            :                 hiwater_rss << (PAGE_SHIFT-10),
      62                 :            :                 total_rss << (PAGE_SHIFT-10),
      63                 :            :                 data << (PAGE_SHIFT-10),
      64                 :            :                 mm->stack_vm << (PAGE_SHIFT-10), text, lib,
      65                 :          0 :                 (PTRS_PER_PTE * sizeof(pte_t) *
      66                 :            :                  atomic_long_read(&mm->nr_ptes)) >> 10,
      67                 :            :                 swap << (PAGE_SHIFT-10));
      68                 :       4363 : }
      69                 :            : 
      70                 :          0 : unsigned long task_vsize(struct mm_struct *mm)
      71                 :            : {
      72                 :       5091 :         return PAGE_SIZE * mm->total_vm;
      73                 :            : }
      74                 :            : 
      75                 :          0 : unsigned long task_statm(struct mm_struct *mm,
      76                 :            :                          unsigned long *shared, unsigned long *text,
      77                 :            :                          unsigned long *data, unsigned long *resident)
      78                 :            : {
      79                 :          2 :         *shared = get_mm_counter(mm, MM_FILEPAGES);
      80                 :          4 :         *text = (PAGE_ALIGN(mm->end_code) - (mm->start_code & PAGE_MASK))
      81                 :          2 :                                                                 >> PAGE_SHIFT;
      82                 :          2 :         *data = mm->total_vm - mm->shared_vm;
      83                 :          2 :         *resident = *shared + get_mm_counter(mm, MM_ANONPAGES);
      84                 :          0 :         return mm->total_vm;
      85                 :            : }
      86                 :            : 
      87                 :            : #ifdef CONFIG_NUMA
      88                 :            : /*
      89                 :            :  * These functions are for numa_maps but called in generic **maps seq_file
      90                 :            :  * ->start(), ->stop() ops.
      91                 :            :  *
      92                 :            :  * numa_maps scans all vmas under mmap_sem and checks their mempolicy.
      93                 :            :  * Each mempolicy object is controlled by reference counting. The problem here
      94                 :            :  * is how to avoid accessing dead mempolicy object.
      95                 :            :  *
      96                 :            :  * Because we're holding mmap_sem while reading seq_file, it's safe to access
      97                 :            :  * each vma's mempolicy, no vma objects will never drop refs to mempolicy.
      98                 :            :  *
      99                 :            :  * A task's mempolicy (task->mempolicy) has different behavior. task->mempolicy
     100                 :            :  * is set and replaced under mmap_sem but unrefed and cleared under task_lock().
     101                 :            :  * So, without task_lock(), we cannot trust get_vma_policy() because we cannot
     102                 :            :  * gurantee the task never exits under us. But taking task_lock() around
     103                 :            :  * get_vma_plicy() causes lock order problem.
     104                 :            :  *
     105                 :            :  * To access task->mempolicy without lock, we hold a reference count of an
     106                 :            :  * object pointed by task->mempolicy and remember it. This will guarantee
     107                 :            :  * that task->mempolicy points to an alive object or NULL in numa_maps accesses.
     108                 :            :  */
     109                 :            : static void hold_task_mempolicy(struct proc_maps_private *priv)
     110                 :            : {
     111                 :            :         struct task_struct *task = priv->task;
     112                 :            : 
     113                 :            :         task_lock(task);
     114                 :            :         priv->task_mempolicy = task->mempolicy;
     115                 :            :         mpol_get(priv->task_mempolicy);
     116                 :            :         task_unlock(task);
     117                 :            : }
     118                 :            : static void release_task_mempolicy(struct proc_maps_private *priv)
     119                 :            : {
     120                 :            :         mpol_put(priv->task_mempolicy);
     121                 :            : }
     122                 :            : #else
     123                 :            : static void hold_task_mempolicy(struct proc_maps_private *priv)
     124                 :            : {
     125                 :            : }
     126                 :            : static void release_task_mempolicy(struct proc_maps_private *priv)
     127                 :            : {
     128                 :            : }
     129                 :            : #endif
     130                 :            : 
     131                 :          0 : static void seq_print_vma_name(struct seq_file *m, struct vm_area_struct *vma)
     132                 :            : {
     133                 :            :         const char __user *name = vma_get_anon_name(vma);
     134                 :          0 :         struct mm_struct *mm = vma->vm_mm;
     135                 :            : 
     136                 :            :         unsigned long page_start_vaddr;
     137                 :            :         unsigned long page_offset;
     138                 :            :         unsigned long num_pages;
     139                 :            :         unsigned long max_len = NAME_MAX;
     140                 :            :         int i;
     141                 :            : 
     142                 :          0 :         page_start_vaddr = (unsigned long)name & PAGE_MASK;
     143                 :          0 :         page_offset = (unsigned long)name - page_start_vaddr;
     144                 :          0 :         num_pages = DIV_ROUND_UP(page_offset + max_len, PAGE_SIZE);
     145                 :            : 
     146                 :          0 :         seq_puts(m, "[anon:");
     147                 :            : 
     148         [ #  # ]:          0 :         for (i = 0; i < num_pages; i++) {
     149                 :            :                 int len;
     150                 :            :                 int write_len;
     151                 :            :                 const char *kaddr;
     152                 :            :                 long pages_pinned;
     153                 :            :                 struct page *page;
     154                 :            : 
     155                 :          0 :                 pages_pinned = get_user_pages(current, mm, page_start_vaddr,
     156                 :            :                                 1, 0, 0, &page, NULL);
     157         [ #  # ]:          0 :                 if (pages_pinned < 1) {
     158                 :          0 :                         seq_puts(m, "<fault>]");
     159                 :          0 :                         return;
     160                 :            :                 }
     161                 :            : 
     162                 :          0 :                 kaddr = (const char *)kmap(page);
     163                 :          0 :                 len = min(max_len, PAGE_SIZE - page_offset);
     164                 :          0 :                 write_len = strnlen(kaddr + page_offset, len);
     165                 :          0 :                 seq_write(m, kaddr + page_offset, write_len);
     166                 :          0 :                 kunmap(page);
     167                 :          0 :                 put_page(page);
     168                 :            : 
     169                 :            :                 /* if strnlen hit a null terminator then we're done */
     170         [ #  # ]:          0 :                 if (write_len != len)
     171                 :            :                         break;
     172                 :            : 
     173                 :          0 :                 max_len -= len;
     174                 :            :                 page_offset = 0;
     175                 :          0 :                 page_start_vaddr += PAGE_SIZE;
     176                 :            :         }
     177                 :            : 
     178                 :          0 :         seq_putc(m, ']');
     179                 :            : }
     180                 :            : 
     181                 :      59483 : static void vma_stop(struct proc_maps_private *priv, struct vm_area_struct *vma)
     182                 :            : {
     183 [ +  + ][ +  + ]:      59483 :         if (vma && vma != priv->tail_vma) {
     184                 :      59097 :                 struct mm_struct *mm = vma->vm_mm;
     185                 :            :                 release_task_mempolicy(priv);
     186                 :      59097 :                 up_read(&mm->mmap_sem);
     187                 :      59097 :                 mmput(mm);
     188                 :            :         }
     189                 :          0 : }
     190                 :            : 
     191                 :          0 : static void *m_start(struct seq_file *m, loff_t *pos)
     192                 :            : {
     193                 :      59192 :         struct proc_maps_private *priv = m->private;
     194                 :      59192 :         unsigned long last_addr = m->version;
     195                 :            :         struct mm_struct *mm;
     196                 :            :         struct vm_area_struct *vma, *tail_vma = NULL;
     197                 :      59192 :         loff_t l = *pos;
     198                 :            : 
     199                 :            :         /* Clear the per syscall fields in priv */
     200                 :      59192 :         priv->task = NULL;
     201                 :      59192 :         priv->tail_vma = NULL;
     202                 :            : 
     203                 :            :         /*
     204                 :            :          * We remember last_addr rather than next_addr to hit with
     205                 :            :          * mmap_cache most of the time. We have zero last_addr at
     206                 :            :          * the beginning and also after lseek. We will have -1 last_addr
     207                 :            :          * after the end of the vmas.
     208                 :            :          */
     209                 :            : 
     210         [ +  + ]:      59192 :         if (last_addr == -1UL)
     211                 :            :                 return NULL;
     212                 :            : 
     213                 :      59190 :         priv->task = get_pid_task(priv->pid, PIDTYPE_PID);
     214         [ +  - ]:      59190 :         if (!priv->task)
     215                 :            :                 return ERR_PTR(-ESRCH);
     216                 :            : 
     217                 :      59190 :         mm = mm_access(priv->task, PTRACE_MODE_READ);
     218 [ +  - ][ +  - ]:      59190 :         if (!mm || IS_ERR(mm))
     219                 :            :                 return mm;
     220                 :      59190 :         down_read(&mm->mmap_sem);
     221                 :            : 
     222                 :      59190 :         tail_vma = get_gate_vma(priv->task->mm);
     223                 :      59190 :         priv->tail_vma = tail_vma;
     224                 :            :         hold_task_mempolicy(priv);
     225                 :            :         /* Start with last addr hint */
     226                 :      59190 :         vma = find_vma(mm, last_addr);
     227         [ +  + ]:      59190 :         if (last_addr && vma) {
     228                 :      58953 :                 vma = vma->vm_next;
     229                 :      58953 :                 goto out;
     230                 :            :         }
     231                 :            : 
     232                 :            :         /*
     233                 :            :          * Check the vma index is within the range and do
     234                 :            :          * sequential scan until m_index.
     235                 :            :          */
     236                 :            :         vma = NULL;
     237         [ +  + ]:        237 :         if ((unsigned long)l < mm->map_count) {
     238                 :        144 :                 vma = mm->mmap;
     239 [ +  + ][ +  - ]:        161 :                 while (l-- && vma)
     240                 :         17 :                         vma = vma->vm_next;
     241                 :            :                 goto out;
     242                 :            :         }
     243                 :            : 
     244         [ +  + ]:         93 :         if (l != mm->map_count)
     245                 :            :                 tail_vma = NULL; /* After gate vma */
     246                 :            : 
     247                 :            : out:
     248         [ +  + ]:      59190 :         if (vma)
     249                 :            :                 return vma;
     250                 :            : 
     251                 :            :         release_task_mempolicy(priv);
     252                 :            :         /* End of vmas has been reached */
     253         [ +  + ]:         93 :         m->version = (tail_vma != NULL)? 0: -1UL;
     254                 :         93 :         up_read(&mm->mmap_sem);
     255                 :         93 :         mmput(mm);
     256                 :         93 :         return tail_vma;
     257                 :            : }
     258                 :            : 
     259                 :          0 : static void *m_next(struct seq_file *m, void *v, loff_t *pos)
     260                 :            : {
     261                 :     816440 :         struct proc_maps_private *priv = m->private;
     262                 :            :         struct vm_area_struct *vma = v;
     263                 :     816440 :         struct vm_area_struct *tail_vma = priv->tail_vma;
     264                 :            : 
     265                 :     816440 :         (*pos)++;
     266 [ +  + ][ +  + ]:     816440 :         if (vma && (vma != tail_vma) && vma->vm_next)
     267                 :            :                 return vma->vm_next;
     268                 :        291 :         vma_stop(priv, vma);
     269         [ +  + ]:     816731 :         return (vma != tail_vma)? tail_vma: NULL;
     270                 :            : }
     271                 :            : 
     272                 :          0 : static void m_stop(struct seq_file *m, void *v)
     273                 :            : {
     274                 :      59192 :         struct proc_maps_private *priv = m->private;
     275                 :            :         struct vm_area_struct *vma = v;
     276                 :            : 
     277         [ +  - ]:      59192 :         if (!IS_ERR(vma))
     278                 :      59192 :                 vma_stop(priv, vma);
     279         [ +  + ]:      59192 :         if (priv->task)
     280                 :            :                 put_task_struct(priv->task);
     281                 :          0 : }
     282                 :            : 
     283                 :          0 : static int do_maps_open(struct inode *inode, struct file *file,
     284                 :            :                         const struct seq_operations *ops)
     285                 :            : {
     286                 :            :         struct proc_maps_private *priv;
     287                 :            :         int ret = -ENOMEM;
     288                 :            :         priv = kzalloc(sizeof(*priv), GFP_KERNEL);
     289         [ +  - ]:        143 :         if (priv) {
     290                 :        143 :                 priv->pid = proc_pid(inode);
     291                 :        143 :                 ret = seq_open(file, ops);
     292         [ +  - ]:        286 :                 if (!ret) {
     293                 :        143 :                         struct seq_file *m = file->private_data;
     294                 :        143 :                         m->private = priv;
     295                 :            :                 } else {
     296                 :          0 :                         kfree(priv);
     297                 :            :                 }
     298                 :            :         }
     299                 :        143 :         return ret;
     300                 :            : }
     301                 :            : 
     302                 :            : static void
     303                 :          0 : show_map_vma(struct seq_file *m, struct vm_area_struct *vma, int is_pid)
     304                 :            : {
     305                 :     875397 :         struct mm_struct *mm = vma->vm_mm;
     306                 :     875397 :         struct file *file = vma->vm_file;
     307                 :     875397 :         struct proc_maps_private *priv = m->private;
     308                 :     875397 :         struct task_struct *task = priv->task;
     309                 :     875397 :         vm_flags_t flags = vma->vm_flags;
     310                 :            :         unsigned long ino = 0;
     311                 :            :         unsigned long long pgoff = 0;
     312                 :            :         unsigned long start, end;
     313                 :            :         dev_t dev = 0;
     314                 :            :         const char *name = NULL;
     315                 :            : 
     316         [ +  + ]:     875397 :         if (file) {
     317                 :     874238 :                 struct inode *inode = file_inode(vma->vm_file);
     318                 :     874238 :                 dev = inode->i_sb->s_dev;
     319                 :     874238 :                 ino = inode->i_ino;
     320                 :     874238 :                 pgoff = ((loff_t)vma->vm_pgoff) << PAGE_SHIFT;
     321                 :            :         }
     322                 :            : 
     323                 :            :         /* We don't show the stack guard page in /proc/maps */
     324                 :     875397 :         start = vma->vm_start;
     325         [ +  + ]:     875397 :         if (stack_guard_page_start(vma, start))
     326                 :        141 :                 start += PAGE_SIZE;
     327                 :     875397 :         end = vma->vm_end;
     328                 :            :         if (stack_guard_page_end(vma, end))
     329                 :            :                 end -= PAGE_SIZE;
     330                 :            : 
     331                 :            :         seq_setwidth(m, 25 + sizeof(void *) * 6 - 1);
     332 [ +  + ][ +  + ]:     875397 :         seq_printf(m, "%08lx-%08lx %c%c%c%c %08llx %02x:%02x %lu ",
         [ #  # ][ #  # ]
     333                 :            :                         start,
     334                 :            :                         end,
     335                 :     875397 :                         flags & VM_READ ? 'r' : '-',
     336                 :     875397 :                         flags & VM_WRITE ? 'w' : '-',
     337                 :          0 :                         flags & VM_EXEC ? 'x' : '-',
     338                 :          0 :                         flags & VM_MAYSHARE ? 's' : 'p',
     339                 :            :                         pgoff,
     340                 :            :                         MAJOR(dev), MINOR(dev), ino);
     341                 :            : 
     342                 :            :         /*
     343                 :            :          * Print the dentry name for named mappings, and a
     344                 :            :          * special [heap] marker for the heap:
     345                 :            :          */
     346         [ +  + ]:     875397 :         if (file) {
     347                 :     874238 :                 seq_pad(m, ' ');
     348                 :     874238 :                 seq_path(m, &file->f_path, "\n");
     349                 :     874238 :                 goto done;
     350                 :            :         }
     351                 :            : 
     352                 :       1159 :         name = arch_vma_name(vma);
     353         [ +  + ]:       1159 :         if (!name) {
     354                 :            :                 pid_t tid;
     355                 :            : 
     356         [ +  - ]:        865 :                 if (!mm) {
     357                 :            :                         name = "[vdso]";
     358                 :            :                         goto done;
     359                 :            :                 }
     360                 :            : 
     361 [ +  + ][ +  + ]:        865 :                 if (vma->vm_start <= mm->brk &&
     362                 :        286 :                     vma->vm_end >= mm->start_brk) {
     363                 :            :                         name = "[heap]";
     364                 :            :                         goto done;
     365                 :            :                 }
     366                 :            : 
     367                 :        722 :                 tid = vm_is_stack(task, vma, is_pid);
     368                 :            : 
     369         [ +  + ]:        722 :                 if (tid != 0) {
     370                 :            :                         /*
     371                 :            :                          * Thread stack in /proc/PID/task/TID/maps or
     372                 :            :                          * the main process stack.
     373                 :            :                          */
     374 [ +  + ][ +  - ]:        142 :                         if (!is_pid || (vma->vm_start <= mm->start_stack &&
                 [ -  + ]
     375                 :        140 :                             vma->vm_end >= mm->start_stack)) {
     376                 :            :                                 name = "[stack]";
     377                 :            :                         } else {
     378                 :            :                                 /* Thread stack in /proc/PID/maps */
     379                 :          0 :                                 seq_pad(m, ' ');
     380                 :          0 :                                 seq_printf(m, "[stack:%d]", tid);
     381                 :            :                         }
     382                 :            :                         goto done;
     383                 :            :                 }
     384                 :            : 
     385         [ -  + ]:        580 :                 if (vma_get_anon_name(vma)) {
     386                 :          0 :                         seq_pad(m, ' ');
     387                 :          0 :                         seq_print_vma_name(m, vma);
     388                 :            :                 }
     389                 :            :         }
     390                 :            : 
     391                 :            : done:
     392         [ +  + ]:     875397 :         if (name) {
     393                 :        579 :                 seq_pad(m, ' ');
     394                 :        579 :                 seq_puts(m, name);
     395                 :            :         }
     396                 :     875397 :         seq_putc(m, '\n');
     397                 :     875397 : }
     398                 :            : 
     399                 :          0 : static int show_map(struct seq_file *m, void *v, int is_pid)
     400                 :            : {
     401                 :            :         struct vm_area_struct *vma = v;
     402                 :     875363 :         struct proc_maps_private *priv = m->private;
     403                 :     875363 :         struct task_struct *task = priv->task;
     404                 :            : 
     405                 :     875363 :         show_map_vma(m, vma, is_pid);
     406                 :            : 
     407         [ +  - ]:     875363 :         if (m->count < m->size)  /* vma is copied successfully */
     408         [ +  + ]:     875363 :                 m->version = (vma != get_gate_vma(task->mm))
     409                 :     875214 :                         ? vma->vm_start : 0;
     410                 :     875363 :         return 0;
     411                 :            : }
     412                 :            : 
     413                 :          0 : static int show_pid_map(struct seq_file *m, void *v)
     414                 :            : {
     415                 :     875346 :         return show_map(m, v, 1);
     416                 :            : }
     417                 :            : 
     418                 :          0 : static int show_tid_map(struct seq_file *m, void *v)
     419                 :            : {
     420                 :         17 :         return show_map(m, v, 0);
     421                 :            : }
     422                 :            : 
     423                 :            : static const struct seq_operations proc_pid_maps_op = {
     424                 :            :         .start  = m_start,
     425                 :            :         .next   = m_next,
     426                 :            :         .stop   = m_stop,
     427                 :            :         .show   = show_pid_map
     428                 :            : };
     429                 :            : 
     430                 :            : static const struct seq_operations proc_tid_maps_op = {
     431                 :            :         .start  = m_start,
     432                 :            :         .next   = m_next,
     433                 :            :         .stop   = m_stop,
     434                 :            :         .show   = show_tid_map
     435                 :            : };
     436                 :            : 
     437                 :          0 : static int pid_maps_open(struct inode *inode, struct file *file)
     438                 :            : {
     439                 :        140 :         return do_maps_open(inode, file, &proc_pid_maps_op);
     440                 :            : }
     441                 :            : 
     442                 :          0 : static int tid_maps_open(struct inode *inode, struct file *file)
     443                 :            : {
     444                 :          1 :         return do_maps_open(inode, file, &proc_tid_maps_op);
     445                 :            : }
     446                 :            : 
     447                 :            : const struct file_operations proc_pid_maps_operations = {
     448                 :            :         .open           = pid_maps_open,
     449                 :            :         .read           = seq_read,
     450                 :            :         .llseek         = seq_lseek,
     451                 :            :         .release        = seq_release_private,
     452                 :            : };
     453                 :            : 
     454                 :            : const struct file_operations proc_tid_maps_operations = {
     455                 :            :         .open           = tid_maps_open,
     456                 :            :         .read           = seq_read,
     457                 :            :         .llseek         = seq_lseek,
     458                 :            :         .release        = seq_release_private,
     459                 :            : };
     460                 :            : 
     461                 :            : /*
     462                 :            :  * Proportional Set Size(PSS): my share of RSS.
     463                 :            :  *
     464                 :            :  * PSS of a process is the count of pages it has in memory, where each
     465                 :            :  * page is divided by the number of processes sharing it.  So if a
     466                 :            :  * process has 1000 pages all to itself, and 1000 shared with one other
     467                 :            :  * process, its PSS will be 1500.
     468                 :            :  *
     469                 :            :  * To keep (accumulated) division errors low, we adopt a 64bit
     470                 :            :  * fixed-point pss counter to minimize division errors. So (pss >>
     471                 :            :  * PSS_SHIFT) would be the real byte count.
     472                 :            :  *
     473                 :            :  * A shift of 12 before division means (assuming 4K page size):
     474                 :            :  *      - 1M 3-user-pages add up to 8KB errors;
     475                 :            :  *      - supports mapcount up to 2^24, or 16M;
     476                 :            :  *      - supports PSS up to 2^52 bytes, or 4PB.
     477                 :            :  */
     478                 :            : #define PSS_SHIFT 12
     479                 :            : 
     480                 :            : #ifdef CONFIG_PROC_PAGE_MONITOR
     481                 :            : struct mem_size_stats {
     482                 :            :         struct vm_area_struct *vma;
     483                 :            :         unsigned long resident;
     484                 :            :         unsigned long shared_clean;
     485                 :            :         unsigned long shared_dirty;
     486                 :            :         unsigned long private_clean;
     487                 :            :         unsigned long private_dirty;
     488                 :            :         unsigned long referenced;
     489                 :            :         unsigned long anonymous;
     490                 :            :         unsigned long anonymous_thp;
     491                 :            :         unsigned long swap;
     492                 :            :         unsigned long nonlinear;
     493                 :            :         u64 pss;
     494                 :            : };
     495                 :            : 
     496                 :            : 
     497                 :          0 : static void smaps_pte_entry(pte_t ptent, unsigned long addr,
     498                 :            :                 unsigned long ptent_size, struct mm_walk *walk)
     499                 :            : {
     500                 :        788 :         struct mem_size_stats *mss = walk->private;
     501                 :        788 :         struct vm_area_struct *vma = mss->vma;
     502                 :            :         pgoff_t pgoff = linear_page_index(vma, addr);
     503                 :       1121 :         struct page *page = NULL;
     504                 :            :         int mapcount;
     505                 :            : 
     506         [ +  + ]:        788 :         if (pte_present(ptent)) {
     507                 :        333 :                 page = vm_normal_page(vma, addr, ptent);
     508         [ -  + ]:        455 :         } else if (is_swap_pte(ptent)) {
     509                 :            :                 swp_entry_t swpent = pte_to_swp_entry(ptent);
     510                 :            : 
     511         [ #  # ]:          0 :                 if (!non_swap_entry(swpent))
     512                 :          0 :                         mss->swap += ptent_size;
     513         [ #  # ]:          0 :                 else if (is_migration_entry(swpent))
     514                 :            :                         page = migration_entry_to_page(swpent);
     515         [ -  + ]:        455 :         } else if (pte_file(ptent)) {
     516         [ #  # ]:          0 :                 if (pte_to_pgoff(ptent) != pgoff)
     517                 :          0 :                         mss->nonlinear += ptent_size;
     518                 :            :         }
     519                 :            : 
     520         [ +  + ]:       1576 :         if (!page)
     521                 :        788 :                 return;
     522                 :            : 
     523         [ +  + ]:       1121 :         if (PageAnon(page))
     524                 :         65 :                 mss->anonymous += ptent_size;
     525                 :            : 
     526         [ -  + ]:       1121 :         if (page->index != pgoff)
     527                 :          0 :                 mss->nonlinear += ptent_size;
     528                 :            : 
     529                 :        333 :         mss->resident += ptent_size;
     530                 :            :         /* Accumulate the size in pages that have been accessed. */
     531 [ -  + ][ #  # ]:       1121 :         if (pte_young(ptent) || PageReferenced(page))
     532                 :        333 :                 mss->referenced += ptent_size;
     533                 :            :         mapcount = page_mapcount(page);
     534         [ +  + ]:        333 :         if (mapcount >= 2) {
     535 [ +  - ][ -  + ]:        198 :                 if (pte_dirty(ptent) || PageDirty(page))
     536                 :          0 :                         mss->shared_dirty += ptent_size;
     537                 :            :                 else
     538                 :        198 :                         mss->shared_clean += ptent_size;
     539                 :        198 :                 mss->pss += (ptent_size << PSS_SHIFT) / mapcount;
     540                 :            :         } else {
     541 [ +  + ][ -  + ]:        135 :                 if (pte_dirty(ptent) || PageDirty(page))
     542                 :         65 :                         mss->private_dirty += ptent_size;
     543                 :            :                 else
     544                 :         70 :                         mss->private_clean += ptent_size;
     545                 :        135 :                 mss->pss += (ptent_size << PSS_SHIFT);
     546                 :            :         }
     547                 :            : }
     548                 :            : 
     549                 :          0 : static int smaps_pte_range(pmd_t *pmd, unsigned long addr, unsigned long end,
     550                 :        788 :                            struct mm_walk *walk)
     551                 :            : {
     552                 :            :         struct mem_size_stats *mss = walk->private;
     553                 :            :         struct vm_area_struct *vma = mss->vma;
     554                 :            :         pte_t *pte;
     555                 :            :         spinlock_t *ptl;
     556                 :            : 
     557                 :            :         if (pmd_trans_huge_lock(pmd, vma, &ptl) == 1) {
     558                 :            :                 smaps_pte_entry(*(pte_t *)pmd, addr, HPAGE_PMD_SIZE, walk);
     559                 :            :                 spin_unlock(ptl);
     560                 :            :                 mss->anonymous_thp += HPAGE_PMD_SIZE;
     561                 :            :                 return 0;
     562                 :            :         }
     563                 :            : 
     564                 :            :         if (pmd_trans_unstable(pmd))
     565                 :            :                 return 0;
     566                 :            :         /*
     567                 :            :          * The mmap_sem held all the way back in m_start() is what
     568                 :            :          * keeps khugepaged out of here and from collapsing things
     569                 :            :          * in here.
     570                 :            :          */
     571                 :         32 :         pte = pte_offset_map_lock(vma->vm_mm, pmd, addr, &ptl);
     572         [ +  + ]:        852 :         for (; addr != end; pte++, addr += PAGE_SIZE)
     573                 :        788 :                 smaps_pte_entry(*pte, addr, PAGE_SIZE, walk);
     574                 :         32 :         pte_unmap_unlock(pte - 1, ptl);
     575                 :         32 :         cond_resched();
     576                 :            :         return 0;
     577                 :            : }
     578                 :            : 
     579                 :         34 : static void show_smap_vma_flags(struct seq_file *m, struct vm_area_struct *vma)
     580                 :            : {
     581                 :            :         /*
     582                 :            :          * Don't forget to update Documentation/ on changes.
     583                 :            :          */
     584                 :            :         static const char mnemonics[BITS_PER_LONG][2] = {
     585                 :            :                 /*
     586                 :            :                  * In case if we meet a flag we don't know about.
     587                 :            :                  */
     588                 :            :                 [0 ... (BITS_PER_LONG-1)] = "??",
     589                 :            : 
     590                 :            :                 [ilog2(VM_READ)]        = "rd",
     591                 :            :                 [ilog2(VM_WRITE)]       = "wr",
     592                 :            :                 [ilog2(VM_EXEC)]        = "ex",
     593                 :            :                 [ilog2(VM_SHARED)]      = "sh",
     594                 :            :                 [ilog2(VM_MAYREAD)]     = "mr",
     595                 :            :                 [ilog2(VM_MAYWRITE)]    = "mw",
     596                 :            :                 [ilog2(VM_MAYEXEC)]     = "me",
     597                 :            :                 [ilog2(VM_MAYSHARE)]    = "ms",
     598                 :            :                 [ilog2(VM_GROWSDOWN)]   = "gd",
     599                 :            :                 [ilog2(VM_PFNMAP)]      = "pf",
     600                 :            :                 [ilog2(VM_DENYWRITE)]   = "dw",
     601                 :            :                 [ilog2(VM_LOCKED)]      = "lo",
     602                 :            :                 [ilog2(VM_IO)]          = "io",
     603                 :            :                 [ilog2(VM_SEQ_READ)]    = "sr",
     604                 :            :                 [ilog2(VM_RAND_READ)]   = "rr",
     605                 :            :                 [ilog2(VM_DONTCOPY)]    = "dc",
     606                 :            :                 [ilog2(VM_DONTEXPAND)]  = "de",
     607                 :            :                 [ilog2(VM_ACCOUNT)]     = "ac",
     608                 :            :                 [ilog2(VM_NORESERVE)]   = "nr",
     609                 :            :                 [ilog2(VM_HUGETLB)]     = "ht",
     610                 :            :                 [ilog2(VM_NONLINEAR)]   = "nl",
     611                 :            :                 [ilog2(VM_ARCH_1)]      = "ar",
     612                 :            :                 [ilog2(VM_DONTDUMP)]    = "dd",
     613                 :            : #ifdef CONFIG_MEM_SOFT_DIRTY
     614                 :            :                 [ilog2(VM_SOFTDIRTY)]   = "sd",
     615                 :            : #endif
     616                 :            :                 [ilog2(VM_MIXEDMAP)]    = "mm",
     617                 :            :                 [ilog2(VM_HUGEPAGE)]    = "hg",
     618                 :            :                 [ilog2(VM_NOHUGEPAGE)]  = "nh",
     619                 :            :                 [ilog2(VM_MERGEABLE)]   = "mg",
     620                 :            :         };
     621                 :            :         size_t i;
     622                 :            : 
     623                 :         34 :         seq_puts(m, "VmFlags: ");
     624         [ +  + ]:       1122 :         for (i = 0; i < BITS_PER_LONG; i++) {
     625         [ +  + ]:       1088 :                 if (vma->vm_flags & (1UL << i)) {
     626                 :        196 :                         seq_printf(m, "%c%c ",
     627                 :        392 :                                    mnemonics[i][0], mnemonics[i][1]);
     628                 :            :                 }
     629                 :            :         }
     630                 :         34 :         seq_putc(m, '\n');
     631                 :         34 : }
     632                 :            : 
     633                 :          0 : static int show_smap(struct seq_file *m, void *v, int is_pid)
     634                 :            : {
     635                 :         34 :         struct proc_maps_private *priv = m->private;
     636                 :         34 :         struct task_struct *task = priv->task;
     637                 :         34 :         struct vm_area_struct *vma = v;
     638                 :            :         struct mem_size_stats mss;
     639                 :         68 :         struct mm_walk smaps_walk = {
     640                 :            :                 .pmd_entry = smaps_pte_range,
     641                 :         34 :                 .mm = vma->vm_mm,
     642                 :            :                 .private = &mss,
     643                 :            :         };
     644                 :            : 
     645                 :         34 :         memset(&mss, 0, sizeof mss);
     646                 :         34 :         mss.vma = vma;
     647                 :            :         /* mmap_sem is held in m_start */
     648         [ +  + ]:         34 :         if (vma->vm_mm && !is_vm_hugetlb_page(vma))
     649                 :         32 :                 walk_page_range(vma->vm_start, vma->vm_end, &smaps_walk);
     650                 :            : 
     651                 :         34 :         show_map_vma(m, vma, is_pid);
     652                 :            : 
     653         [ -  + ]:         34 :         seq_printf(m,
     654                 :            :                    "Size:           %8lu kB\n"
     655                 :            :                    "Rss:            %8lu kB\n"
     656                 :            :                    "Pss:            %8lu kB\n"
     657                 :            :                    "Shared_Clean:   %8lu kB\n"
     658                 :            :                    "Shared_Dirty:   %8lu kB\n"
     659                 :            :                    "Private_Clean:  %8lu kB\n"
     660                 :            :                    "Private_Dirty:  %8lu kB\n"
     661                 :            :                    "Referenced:     %8lu kB\n"
     662                 :            :                    "Anonymous:      %8lu kB\n"
     663                 :            :                    "AnonHugePages:  %8lu kB\n"
     664                 :            :                    "Swap:           %8lu kB\n"
     665                 :            :                    "KernelPageSize: %8lu kB\n"
     666                 :            :                    "MMUPageSize:    %8lu kB\n"
     667                 :            :                    "Locked:         %8lu kB\n",
     668                 :         34 :                    (vma->vm_end - vma->vm_start) >> 10,
     669                 :         34 :                    mss.resident >> 10,
     670                 :         34 :                    (unsigned long)(mss.pss >> (10 + PSS_SHIFT)),
     671                 :         34 :                    mss.shared_clean  >> 10,
     672                 :         34 :                    mss.shared_dirty  >> 10,
     673                 :         34 :                    mss.private_clean >> 10,
     674                 :         34 :                    mss.private_dirty >> 10,
     675                 :         34 :                    mss.referenced >> 10,
     676                 :         34 :                    mss.anonymous >> 10,
     677                 :         34 :                    mss.anonymous_thp >> 10,
     678                 :         34 :                    mss.swap >> 10,
     679                 :            :                    vma_kernel_pagesize(vma) >> 10,
     680                 :            :                    vma_mmu_pagesize(vma) >> 10,
     681                 :         34 :                    (vma->vm_flags & VM_LOCKED) ?
     682                 :            :                         (unsigned long)(mss.pss >> (10 + PSS_SHIFT)) : 0);
     683                 :            : 
     684         [ -  + ]:         34 :         if (vma->vm_flags & VM_NONLINEAR)
     685                 :          0 :                 seq_printf(m, "Nonlinear:      %8lu kB\n",
     686                 :          0 :                                 mss.nonlinear >> 10);
     687                 :            : 
     688                 :         34 :         show_smap_vma_flags(m, vma);
     689                 :            : 
     690         [ -  + ]:         34 :         if (vma_get_anon_name(vma)) {
     691                 :          0 :                 seq_puts(m, "Name:           ");
     692                 :          0 :                 seq_print_vma_name(m, vma);
     693                 :          0 :                 seq_putc(m, '\n');
     694                 :            :         }
     695                 :            : 
     696         [ +  - ]:         34 :         if (m->count < m->size)  /* vma is copied successfully */
     697         [ +  + ]:         34 :                 m->version = (vma != get_gate_vma(task->mm))
     698                 :         32 :                         ? vma->vm_start : 0;
     699                 :         34 :         return 0;
     700                 :            : }
     701                 :            : 
     702                 :          0 : static int show_pid_smap(struct seq_file *m, void *v)
     703                 :            : {
     704                 :         17 :         return show_smap(m, v, 1);
     705                 :            : }
     706                 :            : 
     707                 :          0 : static int show_tid_smap(struct seq_file *m, void *v)
     708                 :            : {
     709                 :         17 :         return show_smap(m, v, 0);
     710                 :            : }
     711                 :            : 
     712                 :            : static const struct seq_operations proc_pid_smaps_op = {
     713                 :            :         .start  = m_start,
     714                 :            :         .next   = m_next,
     715                 :            :         .stop   = m_stop,
     716                 :            :         .show   = show_pid_smap
     717                 :            : };
     718                 :            : 
     719                 :            : static const struct seq_operations proc_tid_smaps_op = {
     720                 :            :         .start  = m_start,
     721                 :            :         .next   = m_next,
     722                 :            :         .stop   = m_stop,
     723                 :            :         .show   = show_tid_smap
     724                 :            : };
     725                 :            : 
     726                 :          0 : static int pid_smaps_open(struct inode *inode, struct file *file)
     727                 :            : {
     728                 :          1 :         return do_maps_open(inode, file, &proc_pid_smaps_op);
     729                 :            : }
     730                 :            : 
     731                 :          0 : static int tid_smaps_open(struct inode *inode, struct file *file)
     732                 :            : {
     733                 :          1 :         return do_maps_open(inode, file, &proc_tid_smaps_op);
     734                 :            : }
     735                 :            : 
     736                 :            : const struct file_operations proc_pid_smaps_operations = {
     737                 :            :         .open           = pid_smaps_open,
     738                 :            :         .read           = seq_read,
     739                 :            :         .llseek         = seq_lseek,
     740                 :            :         .release        = seq_release_private,
     741                 :            : };
     742                 :            : 
     743                 :            : const struct file_operations proc_tid_smaps_operations = {
     744                 :            :         .open           = tid_smaps_open,
     745                 :            :         .read           = seq_read,
     746                 :            :         .llseek         = seq_lseek,
     747                 :            :         .release        = seq_release_private,
     748                 :            : };
     749                 :            : 
     750                 :            : /*
     751                 :            :  * We do not want to have constant page-shift bits sitting in
     752                 :            :  * pagemap entries and are about to reuse them some time soon.
     753                 :            :  *
     754                 :            :  * Here's the "migration strategy":
     755                 :            :  * 1. when the system boots these bits remain what they are,
     756                 :            :  *    but a warning about future change is printed in log;
     757                 :            :  * 2. once anyone clears soft-dirty bits via clear_refs file,
     758                 :            :  *    these flag is set to denote, that user is aware of the
     759                 :            :  *    new API and those page-shift bits change their meaning.
     760                 :            :  *    The respective warning is printed in dmesg;
     761                 :            :  * 3. In a couple of releases we will remove all the mentions
     762                 :            :  *    of page-shift in pagemap entries.
     763                 :            :  */
     764                 :            : 
     765                 :            : static bool soft_dirty_cleared __read_mostly;
     766                 :            : 
     767                 :            : enum clear_refs_types {
     768                 :            :         CLEAR_REFS_ALL = 1,
     769                 :            :         CLEAR_REFS_ANON,
     770                 :            :         CLEAR_REFS_MAPPED,
     771                 :            :         CLEAR_REFS_SOFT_DIRTY,
     772                 :            :         CLEAR_REFS_LAST,
     773                 :            : };
     774                 :            : 
     775                 :            : struct clear_refs_private {
     776                 :            :         struct vm_area_struct *vma;
     777                 :            :         enum clear_refs_types type;
     778                 :            : };
     779                 :            : 
     780                 :            : static inline void clear_soft_dirty(struct vm_area_struct *vma,
     781                 :            :                 unsigned long addr, pte_t *pte)
     782                 :            : {
     783                 :            : #ifdef CONFIG_MEM_SOFT_DIRTY
     784                 :            :         /*
     785                 :            :          * The soft-dirty tracker uses #PF-s to catch writes
     786                 :            :          * to pages, so write-protect the pte as well. See the
     787                 :            :          * Documentation/vm/soft-dirty.txt for full description
     788                 :            :          * of how soft-dirty works.
     789                 :            :          */
     790                 :            :         pte_t ptent = *pte;
     791                 :            : 
     792                 :            :         if (pte_present(ptent)) {
     793                 :            :                 ptent = pte_wrprotect(ptent);
     794                 :            :                 ptent = pte_clear_flags(ptent, _PAGE_SOFT_DIRTY);
     795                 :            :         } else if (is_swap_pte(ptent)) {
     796                 :            :                 ptent = pte_swp_clear_soft_dirty(ptent);
     797                 :            :         } else if (pte_file(ptent)) {
     798                 :            :                 ptent = pte_file_clear_soft_dirty(ptent);
     799                 :            :         }
     800                 :            : 
     801                 :            :         if (vma->vm_flags & VM_SOFTDIRTY)
     802                 :            :                 vma->vm_flags &= ~VM_SOFTDIRTY;
     803                 :            : 
     804                 :            :         set_pte_at(vma->vm_mm, addr, pte, ptent);
     805                 :            : #endif
     806                 :            : }
     807                 :            : 
     808                 :          0 : static int clear_refs_pte_range(pmd_t *pmd, unsigned long addr,
     809                 :            :                                 unsigned long end, struct mm_walk *walk)
     810                 :            : {
     811                 :          0 :         struct clear_refs_private *cp = walk->private;
     812                 :          0 :         struct vm_area_struct *vma = cp->vma;
     813                 :            :         pte_t *pte, ptent;
     814                 :            :         spinlock_t *ptl;
     815                 :            :         struct page *page;
     816                 :            : 
     817                 :            :         split_huge_page_pmd(vma, addr, pmd);
     818                 :            :         if (pmd_trans_unstable(pmd))
     819                 :            :                 return 0;
     820                 :            : 
     821                 :          0 :         pte = pte_offset_map_lock(vma->vm_mm, pmd, addr, &ptl);
     822         [ #  # ]:          0 :         for (; addr != end; pte++, addr += PAGE_SIZE) {
     823                 :          0 :                 ptent = *pte;
     824                 :            : 
     825         [ #  # ]:          0 :                 if (cp->type == CLEAR_REFS_SOFT_DIRTY) {
     826                 :            :                         clear_soft_dirty(vma, addr, pte);
     827                 :          0 :                         continue;
     828                 :            :                 }
     829                 :            : 
     830         [ #  # ]:          0 :                 if (!pte_present(ptent))
     831                 :          0 :                         continue;
     832                 :            : 
     833                 :          0 :                 page = vm_normal_page(vma, addr, ptent);
     834         [ #  # ]:          0 :                 if (!page)
     835                 :          0 :                         continue;
     836                 :            : 
     837                 :            :                 /* Clear accessed and referenced bits. */
     838                 :            :                 ptep_test_and_clear_young(vma, addr, pte);
     839                 :            :                 ClearPageReferenced(page);
     840                 :            :         }
     841                 :          0 :         pte_unmap_unlock(pte - 1, ptl);
     842                 :          0 :         cond_resched();
     843                 :            :         return 0;
     844                 :            : }
     845                 :            : 
     846                 :          0 : static ssize_t clear_refs_write(struct file *file, const char __user *buf,
     847                 :            :                                 size_t count, loff_t *ppos)
     848                 :            : {
     849                 :            :         struct task_struct *task;
     850                 :            :         char buffer[PROC_NUMBUF];
     851                 :            :         struct mm_struct *mm;
     852                 :            :         struct vm_area_struct *vma;
     853                 :            :         enum clear_refs_types type;
     854                 :            :         int itype;
     855                 :            :         int rv;
     856                 :            : 
     857                 :          0 :         memset(buffer, 0, sizeof(buffer));
     858         [ #  # ]:          0 :         if (count > sizeof(buffer) - 1)
     859                 :            :                 count = sizeof(buffer) - 1;
     860         [ #  # ]:          0 :         if (copy_from_user(buffer, buf, count))
     861                 :            :                 return -EFAULT;
     862                 :          0 :         rv = kstrtoint(strstrip(buffer), 10, &itype);
     863         [ #  # ]:          0 :         if (rv < 0)
     864                 :            :                 return rv;
     865                 :          0 :         type = (enum clear_refs_types)itype;
     866         [ #  # ]:          0 :         if (type < CLEAR_REFS_ALL || type >= CLEAR_REFS_LAST)
     867                 :            :                 return -EINVAL;
     868                 :            : 
     869         [ #  # ]:          0 :         if (type == CLEAR_REFS_SOFT_DIRTY) {
     870                 :          0 :                 soft_dirty_cleared = true;
     871         [ #  # ]:          0 :                 pr_warn_once("The pagemap bits 55-60 has changed their meaning! "
     872                 :            :                                 "See the linux/Documentation/vm/pagemap.txt for details.\n");
     873                 :            :         }
     874                 :            : 
     875                 :            :         task = get_proc_task(file_inode(file));
     876         [ #  # ]:          0 :         if (!task)
     877                 :            :                 return -ESRCH;
     878                 :          0 :         mm = get_task_mm(task);
     879         [ #  # ]:          0 :         if (mm) {
     880                 :          0 :                 struct clear_refs_private cp = {
     881                 :            :                         .type = type,
     882                 :            :                 };
     883                 :          0 :                 struct mm_walk clear_refs_walk = {
     884                 :            :                         .pmd_entry = clear_refs_pte_range,
     885                 :            :                         .mm = mm,
     886                 :            :                         .private = &cp,
     887                 :            :                 };
     888                 :          0 :                 down_read(&mm->mmap_sem);
     889                 :            :                 if (type == CLEAR_REFS_SOFT_DIRTY)
     890                 :            :                         mmu_notifier_invalidate_range_start(mm, 0, -1);
     891         [ #  # ]:          0 :                 for (vma = mm->mmap; vma; vma = vma->vm_next) {
     892                 :          0 :                         cp.vma = vma;
     893                 :            :                         if (is_vm_hugetlb_page(vma))
     894                 :            :                                 continue;
     895                 :            :                         /*
     896                 :            :                          * Writing 1 to /proc/pid/clear_refs affects all pages.
     897                 :            :                          *
     898                 :            :                          * Writing 2 to /proc/pid/clear_refs only affects
     899                 :            :                          * Anonymous pages.
     900                 :            :                          *
     901                 :            :                          * Writing 3 to /proc/pid/clear_refs only affects file
     902                 :            :                          * mapped pages.
     903                 :            :                          */
     904 [ #  # ][ #  # ]:          0 :                         if (type == CLEAR_REFS_ANON && vma->vm_file)
     905                 :          0 :                                 continue;
     906 [ #  # ][ #  # ]:          0 :                         if (type == CLEAR_REFS_MAPPED && !vma->vm_file)
     907                 :          0 :                                 continue;
     908                 :          0 :                         walk_page_range(vma->vm_start, vma->vm_end,
     909                 :            :                                         &clear_refs_walk);
     910                 :            :                 }
     911                 :            :                 if (type == CLEAR_REFS_SOFT_DIRTY)
     912                 :            :                         mmu_notifier_invalidate_range_end(mm, 0, -1);
     913                 :          0 :                 flush_tlb_mm(mm);
     914                 :          0 :                 up_read(&mm->mmap_sem);
     915                 :          0 :                 mmput(mm);
     916                 :            :         }
     917                 :            :         put_task_struct(task);
     918                 :            : 
     919                 :          0 :         return count;
     920                 :            : }
     921                 :            : 
     922                 :            : const struct file_operations proc_clear_refs_operations = {
     923                 :            :         .write          = clear_refs_write,
     924                 :            :         .llseek         = noop_llseek,
     925                 :            : };
     926                 :            : 
     927                 :            : typedef struct {
     928                 :            :         u64 pme;
     929                 :            : } pagemap_entry_t;
     930                 :            : 
     931                 :            : struct pagemapread {
     932                 :            :         int pos, len;           /* units: PM_ENTRY_BYTES, not bytes */
     933                 :            :         pagemap_entry_t *buffer;
     934                 :            :         bool v2;
     935                 :            : };
     936                 :            : 
     937                 :            : #define PAGEMAP_WALK_SIZE       (PMD_SIZE)
     938                 :            : #define PAGEMAP_WALK_MASK       (PMD_MASK)
     939                 :            : 
     940                 :            : #define PM_ENTRY_BYTES      sizeof(pagemap_entry_t)
     941                 :            : #define PM_STATUS_BITS      3
     942                 :            : #define PM_STATUS_OFFSET    (64 - PM_STATUS_BITS)
     943                 :            : #define PM_STATUS_MASK      (((1LL << PM_STATUS_BITS) - 1) << PM_STATUS_OFFSET)
     944                 :            : #define PM_STATUS(nr)       (((nr) << PM_STATUS_OFFSET) & PM_STATUS_MASK)
     945                 :            : #define PM_PSHIFT_BITS      6
     946                 :            : #define PM_PSHIFT_OFFSET    (PM_STATUS_OFFSET - PM_PSHIFT_BITS)
     947                 :            : #define PM_PSHIFT_MASK      (((1LL << PM_PSHIFT_BITS) - 1) << PM_PSHIFT_OFFSET)
     948                 :            : #define __PM_PSHIFT(x)      (((u64) (x) << PM_PSHIFT_OFFSET) & PM_PSHIFT_MASK)
     949                 :            : #define PM_PFRAME_MASK      ((1LL << PM_PSHIFT_OFFSET) - 1)
     950                 :            : #define PM_PFRAME(x)        ((x) & PM_PFRAME_MASK)
     951                 :            : /* in "new" pagemap pshift bits are occupied with more status bits */
     952                 :            : #define PM_STATUS2(v2, x)   (__PM_PSHIFT(v2 ? x : PAGE_SHIFT))
     953                 :            : 
     954                 :            : #define __PM_SOFT_DIRTY      (1LL)
     955                 :            : #define PM_PRESENT          PM_STATUS(4LL)
     956                 :            : #define PM_SWAP             PM_STATUS(2LL)
     957                 :            : #define PM_FILE             PM_STATUS(1LL)
     958                 :            : #define PM_NOT_PRESENT(v2)  PM_STATUS2(v2, 0)
     959                 :            : #define PM_END_OF_BUFFER    1
     960                 :            : 
     961                 :            : static inline pagemap_entry_t make_pme(u64 val)
     962                 :            : {
     963                 :        288 :         return (pagemap_entry_t) { .pme = val };
     964                 :            : }
     965                 :            : 
     966                 :            : static int add_to_pagemap(unsigned long addr, pagemap_entry_t *pme,
     967                 :            :                           struct pagemapread *pm)
     968                 :            : {
     969                 :    3967616 :         pm->buffer[pm->pos++] = *pme;
     970 [ +  + ][ +  + ]:    3967904 :         if (pm->pos >= pm->len)
     971                 :            :                 return PM_END_OF_BUFFER;
     972                 :            :         return 0;
     973                 :            : }
     974                 :            : 
     975                 :          0 : static int pagemap_pte_hole(unsigned long start, unsigned long end,
     976                 :            :                                 struct mm_walk *walk)
     977                 :            : {
     978                 :      12192 :         struct pagemapread *pm = walk->private;
     979                 :            :         unsigned long addr;
     980                 :            :         int err = 0;
     981         [ +  - ]:      12192 :         pagemap_entry_t pme = make_pme(PM_NOT_PRESENT(pm->v2));
     982                 :            : 
     983         [ +  + ]:    3910584 :         for (addr = start; addr < end; addr += PAGE_SIZE) {
     984                 :            :                 err = add_to_pagemap(addr, &pme, pm);
     985            [ + ]:    3901440 :                 if (err)
     986                 :            :                         break;
     987                 :            :         }
     988                 :          0 :         return err;
     989                 :            : }
     990                 :            : 
     991                 :          0 : static void pte_to_pagemap_entry(pagemap_entry_t *pme, struct pagemapread *pm,
     992                 :            :                 struct vm_area_struct *vma, unsigned long addr, pte_t pte)
     993                 :            : {
     994                 :            :         u64 frame, flags;
     995                 :      28451 :         struct page *page = NULL;
     996                 :            :         int flags2 = 0;
     997                 :            : 
     998         [ +  + ]:      44916 :         if (pte_present(pte)) {
     999                 :      28451 :                 frame = pte_pfn(pte);
    1000                 :            :                 flags = PM_PRESENT;
    1001                 :      28451 :                 page = vm_normal_page(vma, addr, pte);
    1002                 :            :                 if (pte_soft_dirty(pte))
    1003                 :            :                         flags2 |= __PM_SOFT_DIRTY;
    1004         [ -  + ]:      16465 :         } else if (is_swap_pte(pte)) {
    1005                 :            :                 swp_entry_t entry;
    1006                 :            :                 if (pte_swp_soft_dirty(pte))
    1007                 :            :                         flags2 |= __PM_SOFT_DIRTY;
    1008                 :            :                 entry = pte_to_swp_entry(pte);
    1009                 :          0 :                 frame = swp_type(entry) |
    1010                 :          0 :                         (swp_offset(entry) << MAX_SWAPFILES_SHIFT);
    1011                 :            :                 flags = PM_SWAP;
    1012         [ #  # ]:          0 :                 if (is_migration_entry(entry))
    1013                 :            :                         page = migration_entry_to_page(entry);
    1014                 :            :         } else {
    1015                 :            :                 if (vma->vm_flags & VM_SOFTDIRTY)
    1016                 :            :                         flags2 |= __PM_SOFT_DIRTY;
    1017 [ +  - ][ +  - ]:      16465 :                 *pme = make_pme(PM_NOT_PRESENT(pm->v2) | PM_STATUS2(pm->v2, flags2));
    1018                 :      44916 :                 return;
    1019                 :            :         }
    1020                 :            : 
    1021 [ +  - ][ +  + ]:      73367 :         if (page && !PageAnon(page))
    1022                 :       8994 :                 flags |= PM_FILE;
    1023                 :            :         if ((vma->vm_flags & VM_SOFTDIRTY))
    1024                 :            :                 flags2 |= __PM_SOFT_DIRTY;
    1025                 :            : 
    1026         [ +  - ]:      28451 :         *pme = make_pme(PM_PFRAME(frame) | PM_STATUS2(pm->v2, flags2) | flags);
    1027                 :            : }
    1028                 :            : 
    1029                 :            : #ifdef CONFIG_TRANSPARENT_HUGEPAGE
    1030                 :            : static void thp_pmd_to_pagemap_entry(pagemap_entry_t *pme, struct pagemapread *pm,
    1031                 :            :                 pmd_t pmd, int offset, int pmd_flags2)
    1032                 :            : {
    1033                 :            :         /*
    1034                 :            :          * Currently pmd for thp is always present because thp can not be
    1035                 :            :          * swapped-out, migrated, or HWPOISONed (split in such cases instead.)
    1036                 :            :          * This if-check is just to prepare for future implementation.
    1037                 :            :          */
    1038                 :            :         if (pmd_present(pmd))
    1039                 :            :                 *pme = make_pme(PM_PFRAME(pmd_pfn(pmd) + offset)
    1040                 :            :                                 | PM_STATUS2(pm->v2, pmd_flags2) | PM_PRESENT);
    1041                 :            :         else
    1042                 :            :                 *pme = make_pme(PM_NOT_PRESENT(pm->v2) | PM_STATUS2(pm->v2, pmd_flags2));
    1043                 :            : }
    1044                 :            : #else
    1045                 :            : static inline void thp_pmd_to_pagemap_entry(pagemap_entry_t *pme, struct pagemapread *pm,
    1046                 :            :                 pmd_t pmd, int offset, int pmd_flags2)
    1047                 :            : {
    1048                 :            : }
    1049                 :            : #endif
    1050                 :            : 
    1051                 :          0 : static int pagemap_pte_range(pmd_t *pmd, unsigned long addr, unsigned long end,
    1052                 :            :                              struct mm_walk *walk)
    1053                 :            : {
    1054                 :            :         struct vm_area_struct *vma;
    1055                 :        288 :         struct pagemapread *pm = walk->private;
    1056                 :            :         spinlock_t *ptl;
    1057                 :            :         pte_t *pte;
    1058                 :            :         int err = 0;
    1059         [ +  - ]:        288 :         pagemap_entry_t pme = make_pme(PM_NOT_PRESENT(pm->v2));
    1060                 :            : 
    1061                 :            :         /* find the first VMA at or above 'addr' */
    1062                 :        288 :         vma = find_vma(walk->mm, addr);
    1063                 :            :         if (vma && pmd_trans_huge_lock(pmd, vma, &ptl) == 1) {
    1064                 :            :                 int pmd_flags2;
    1065                 :            : 
    1066                 :            :                 if ((vma->vm_flags & VM_SOFTDIRTY) || pmd_soft_dirty(*pmd))
    1067                 :            :                         pmd_flags2 = __PM_SOFT_DIRTY;
    1068                 :            :                 else
    1069                 :            :                         pmd_flags2 = 0;
    1070                 :            : 
    1071                 :            :                 for (; addr != end; addr += PAGE_SIZE) {
    1072                 :            :                         unsigned long offset;
    1073                 :            : 
    1074                 :            :                         offset = (addr & ~PAGEMAP_WALK_MASK) >>
    1075                 :            :                                         PAGE_SHIFT;
    1076                 :            :                         thp_pmd_to_pagemap_entry(&pme, pm, *pmd, offset, pmd_flags2);
    1077                 :            :                         err = add_to_pagemap(addr, &pme, pm);
    1078                 :            :                         if (err)
    1079                 :            :                                 break;
    1080                 :            :                 }
    1081                 :            :                 spin_unlock(ptl);
    1082                 :            :                 return err;
    1083                 :            :         }
    1084                 :            : 
    1085                 :            :         if (pmd_trans_unstable(pmd))
    1086                 :            :                 return 0;
    1087         [ +  + ]:      66455 :         for (; addr != end; addr += PAGE_SIZE) {
    1088                 :            :                 int flags2;
    1089                 :            : 
    1090                 :            :                 /* check to see if we've left 'vma' behind
    1091                 :            :                  * and need a new, higher one */
    1092 [ +  + ][ +  + ]:      66176 :                 if (vma && (addr >= vma->vm_end)) {
    1093                 :       1516 :                         vma = find_vma(walk->mm, addr);
    1094                 :            :                         if (vma && (vma->vm_flags & VM_SOFTDIRTY))
    1095                 :            :                                 flags2 = __PM_SOFT_DIRTY;
    1096                 :            :                         else
    1097                 :            :                                 flags2 = 0;
    1098 [ +  - ][ +  - ]:       1516 :                         pme = make_pme(PM_NOT_PRESENT(pm->v2) | PM_STATUS2(pm->v2, flags2));
    1099                 :            :                 }
    1100                 :            : 
    1101                 :            :                 /* check that 'vma' actually covers this address,
    1102                 :            :                  * and that it isn't a huge page vma */
    1103 [ +  + ][ +  + ]:      66176 :                 if (vma && (vma->vm_start <= addr) &&
    1104                 :            :                     !is_vm_hugetlb_page(vma)) {
    1105                 :      44916 :                         pte = pte_offset_map(pmd, addr);
    1106                 :      44916 :                         pte_to_pagemap_entry(&pme, pm, vma, addr, *pte);
    1107                 :            :                         /* unmap before userspace copy */
    1108                 :      44916 :                         pte_unmap(pte);
    1109                 :            :                 }
    1110                 :            :                 err = add_to_pagemap(addr, &pme, pm);
    1111         [ +  + ]:      66176 :                 if (err)
    1112                 :            :                         return err;
    1113                 :            :         }
    1114                 :            : 
    1115                 :        279 :         cond_resched();
    1116                 :            : 
    1117                 :        279 :         return err;
    1118                 :            : }
    1119                 :            : 
    1120                 :            : #ifdef CONFIG_HUGETLB_PAGE
    1121                 :            : static void huge_pte_to_pagemap_entry(pagemap_entry_t *pme, struct pagemapread *pm,
    1122                 :            :                                         pte_t pte, int offset, int flags2)
    1123                 :            : {
    1124                 :            :         if (pte_present(pte))
    1125                 :            :                 *pme = make_pme(PM_PFRAME(pte_pfn(pte) + offset)        |
    1126                 :            :                                 PM_STATUS2(pm->v2, flags2)           |
    1127                 :            :                                 PM_PRESENT);
    1128                 :            :         else
    1129                 :            :                 *pme = make_pme(PM_NOT_PRESENT(pm->v2)                       |
    1130                 :            :                                 PM_STATUS2(pm->v2, flags2));
    1131                 :            : }
    1132                 :            : 
    1133                 :            : /* This function walks within one hugetlb entry in the single call */
    1134                 :            : static int pagemap_hugetlb_range(pte_t *pte, unsigned long hmask,
    1135                 :            :                                  unsigned long addr, unsigned long end,
    1136                 :            :                                  struct mm_walk *walk)
    1137                 :            : {
    1138                 :            :         struct pagemapread *pm = walk->private;
    1139                 :            :         struct vm_area_struct *vma;
    1140                 :            :         int err = 0;
    1141                 :            :         int flags2;
    1142                 :            :         pagemap_entry_t pme;
    1143                 :            : 
    1144                 :            :         vma = find_vma(walk->mm, addr);
    1145                 :            :         WARN_ON_ONCE(!vma);
    1146                 :            : 
    1147                 :            :         if (vma && (vma->vm_flags & VM_SOFTDIRTY))
    1148                 :            :                 flags2 = __PM_SOFT_DIRTY;
    1149                 :            :         else
    1150                 :            :                 flags2 = 0;
    1151                 :            : 
    1152                 :            :         for (; addr != end; addr += PAGE_SIZE) {
    1153                 :            :                 int offset = (addr & ~hmask) >> PAGE_SHIFT;
    1154                 :            :                 huge_pte_to_pagemap_entry(&pme, pm, *pte, offset, flags2);
    1155                 :            :                 err = add_to_pagemap(addr, &pme, pm);
    1156                 :            :                 if (err)
    1157                 :            :                         return err;
    1158                 :            :         }
    1159                 :            : 
    1160                 :            :         cond_resched();
    1161                 :            : 
    1162                 :            :         return err;
    1163                 :            : }
    1164                 :            : #endif /* HUGETLB_PAGE */
    1165                 :            : 
    1166                 :            : /*
    1167                 :            :  * /proc/pid/pagemap - an array mapping virtual pages to pfns
    1168                 :            :  *
    1169                 :            :  * For each page in the address space, this file contains one 64-bit entry
    1170                 :            :  * consisting of the following:
    1171                 :            :  *
    1172                 :            :  * Bits 0-54  page frame number (PFN) if present
    1173                 :            :  * Bits 0-4   swap type if swapped
    1174                 :            :  * Bits 5-54  swap offset if swapped
    1175                 :            :  * Bits 55-60 page shift (page size = 1<<page shift)
    1176                 :            :  * Bit  61    page is file-page or shared-anon
    1177                 :            :  * Bit  62    page swapped
    1178                 :            :  * Bit  63    page present
    1179                 :            :  *
    1180                 :            :  * If the page is not present but in swap, then the PFN contains an
    1181                 :            :  * encoding of the swap file number and the page's offset into the
    1182                 :            :  * swap. Unmapped pages return a null PFN. This allows determining
    1183                 :            :  * precisely which pages are mapped (or in swap) and comparing mapped
    1184                 :            :  * pages between processes.
    1185                 :            :  *
    1186                 :            :  * Efficient users of this interface will use /proc/pid/maps to
    1187                 :            :  * determine which areas of memory are actually mapped and llseek to
    1188                 :            :  * skip over unmapped regions.
    1189                 :            :  */
    1190                 :          0 : static ssize_t pagemap_read(struct file *file, char __user *buf,
    1191                 :            :                             size_t count, loff_t *ppos)
    1192                 :            : {
    1193                 :            :         struct task_struct *task = get_proc_task(file_inode(file));
    1194                 :            :         struct mm_struct *mm;
    1195                 :            :         struct pagemapread pm;
    1196                 :            :         int ret = -ESRCH;
    1197                 :      12482 :         struct mm_walk pagemap_walk = {};
    1198                 :            :         unsigned long src;
    1199                 :            :         unsigned long svpfn;
    1200                 :            :         unsigned long start_vaddr;
    1201                 :            :         unsigned long end_vaddr;
    1202                 :            :         int copied = 0;
    1203                 :            : 
    1204         [ +  - ]:      12482 :         if (!task)
    1205                 :            :                 goto out;
    1206                 :            : 
    1207                 :            :         ret = -EINVAL;
    1208                 :            :         /* file position must be aligned */
    1209 [ +  - ][ +  - ]:      12482 :         if ((*ppos % PM_ENTRY_BYTES) || (count % PM_ENTRY_BYTES))
    1210                 :            :                 goto out_task;
    1211                 :            : 
    1212                 :            :         ret = 0;
    1213         [ +  - ]:      12482 :         if (!count)
    1214                 :            :                 goto out_task;
    1215                 :            : 
    1216                 :      12482 :         pm.v2 = soft_dirty_cleared;
    1217                 :      12482 :         pm.len = (PAGEMAP_WALK_SIZE >> PAGE_SHIFT);
    1218                 :      12482 :         pm.buffer = kmalloc(pm.len * PM_ENTRY_BYTES, GFP_TEMPORARY);
    1219                 :            :         ret = -ENOMEM;
    1220         [ +  - ]:      12482 :         if (!pm.buffer)
    1221                 :            :                 goto out_task;
    1222                 :            : 
    1223                 :      12482 :         mm = mm_access(task, PTRACE_MODE_READ);
    1224                 :            :         ret = PTR_ERR(mm);
    1225 [ +  - ][ +  - ]:      12482 :         if (!mm || IS_ERR(mm))
    1226                 :            :                 goto out_free;
    1227                 :            : 
    1228                 :      12482 :         pagemap_walk.pmd_entry = pagemap_pte_range;
    1229                 :      12482 :         pagemap_walk.pte_hole = pagemap_pte_hole;
    1230                 :            : #ifdef CONFIG_HUGETLB_PAGE
    1231                 :            :         pagemap_walk.hugetlb_entry = pagemap_hugetlb_range;
    1232                 :            : #endif
    1233                 :      12482 :         pagemap_walk.mm = mm;
    1234                 :      12482 :         pagemap_walk.private = &pm;
    1235                 :            : 
    1236                 :      12482 :         src = *ppos;
    1237                 :      12482 :         svpfn = src / PM_ENTRY_BYTES;
    1238                 :      12482 :         start_vaddr = svpfn << PAGE_SHIFT;
    1239                 :            :         end_vaddr = TASK_SIZE_OF(task);
    1240                 :            : 
    1241                 :            :         /* watch out for wraparound */
    1242         [ -  + ]:      12482 :         if (svpfn > TASK_SIZE_OF(task) >> PAGE_SHIFT)
    1243                 :            :                 start_vaddr = end_vaddr;
    1244                 :            : 
    1245                 :            :         /*
    1246                 :            :          * The odds are that this will stop walking way
    1247                 :            :          * before end_vaddr, because the length of the
    1248                 :            :          * user buffer is tracked in "pm", and the walk
    1249                 :            :          * will stop when we hit the end of the buffer.
    1250                 :            :          */
    1251                 :            :         ret = 0;
    1252         [ +  + ]:      24962 :         while (count && (start_vaddr < end_vaddr)) {
    1253                 :            :                 int len;
    1254                 :            :                 unsigned long end;
    1255                 :            : 
    1256                 :      12480 :                 pm.pos = 0;
    1257                 :      12480 :                 end = (start_vaddr + PAGEMAP_WALK_SIZE) & PAGEMAP_WALK_MASK;
    1258                 :            :                 /* overflow ? */
    1259         [ -  + ]:      12480 :                 if (end < start_vaddr || end > end_vaddr)
    1260                 :            :                         end = end_vaddr;
    1261                 :      12480 :                 down_read(&mm->mmap_sem);
    1262                 :      12480 :                 ret = walk_page_range(start_vaddr, end, &pagemap_walk);
    1263                 :      12480 :                 up_read(&mm->mmap_sem);
    1264                 :            :                 start_vaddr = end;
    1265                 :            : 
    1266                 :      12480 :                 len = min(count, PM_ENTRY_BYTES * pm.pos);
    1267         [ +  - ]:      12480 :                 if (copy_to_user(buf, pm.buffer, len)) {
    1268                 :            :                         ret = -EFAULT;
    1269                 :            :                         goto out_mm;
    1270                 :            :                 }
    1271                 :      12480 :                 copied += len;
    1272                 :      12480 :                 buf += len;
    1273                 :      12480 :                 count -= len;
    1274                 :            :         }
    1275                 :      12482 :         *ppos += copied;
    1276         [ +  - ]:      12482 :         if (!ret || ret == PM_END_OF_BUFFER)
    1277                 :            :                 ret = copied;
    1278                 :            : 
    1279                 :            : out_mm:
    1280                 :      12482 :         mmput(mm);
    1281                 :            : out_free:
    1282                 :      12482 :         kfree(pm.buffer);
    1283                 :            : out_task:
    1284                 :            :         put_task_struct(task);
    1285                 :            : out:
    1286                 :      12482 :         return ret;
    1287                 :            : }
    1288                 :            : 
    1289                 :          0 : static int pagemap_open(struct inode *inode, struct file *file)
    1290                 :            : {
    1291         [ +  + ]:          3 :         pr_warn_once("Bits 55-60 of /proc/PID/pagemap entries are about "
    1292                 :            :                         "to stop being page-shift some time soon. See the "
    1293                 :            :                         "linux/Documentation/vm/pagemap.txt for details.\n");
    1294                 :          0 :         return 0;
    1295                 :            : }
    1296                 :            : 
    1297                 :            : const struct file_operations proc_pagemap_operations = {
    1298                 :            :         .llseek         = mem_lseek, /* borrow this */
    1299                 :            :         .read           = pagemap_read,
    1300                 :            :         .open           = pagemap_open,
    1301                 :            : };
    1302                 :            : #endif /* CONFIG_PROC_PAGE_MONITOR */
    1303                 :            : 
    1304                 :            : #ifdef CONFIG_NUMA
    1305                 :            : 
    1306                 :            : struct numa_maps {
    1307                 :            :         struct vm_area_struct *vma;
    1308                 :            :         unsigned long pages;
    1309                 :            :         unsigned long anon;
    1310                 :            :         unsigned long active;
    1311                 :            :         unsigned long writeback;
    1312                 :            :         unsigned long mapcount_max;
    1313                 :            :         unsigned long dirty;
    1314                 :            :         unsigned long swapcache;
    1315                 :            :         unsigned long node[MAX_NUMNODES];
    1316                 :            : };
    1317                 :            : 
    1318                 :            : struct numa_maps_private {
    1319                 :            :         struct proc_maps_private proc_maps;
    1320                 :            :         struct numa_maps md;
    1321                 :            : };
    1322                 :            : 
    1323                 :            : static void gather_stats(struct page *page, struct numa_maps *md, int pte_dirty,
    1324                 :            :                         unsigned long nr_pages)
    1325                 :            : {
    1326                 :            :         int count = page_mapcount(page);
    1327                 :            : 
    1328                 :            :         md->pages += nr_pages;
    1329                 :            :         if (pte_dirty || PageDirty(page))
    1330                 :            :                 md->dirty += nr_pages;
    1331                 :            : 
    1332                 :            :         if (PageSwapCache(page))
    1333                 :            :                 md->swapcache += nr_pages;
    1334                 :            : 
    1335                 :            :         if (PageActive(page) || PageUnevictable(page))
    1336                 :            :                 md->active += nr_pages;
    1337                 :            : 
    1338                 :            :         if (PageWriteback(page))
    1339                 :            :                 md->writeback += nr_pages;
    1340                 :            : 
    1341                 :            :         if (PageAnon(page))
    1342                 :            :                 md->anon += nr_pages;
    1343                 :            : 
    1344                 :            :         if (count > md->mapcount_max)
    1345                 :            :                 md->mapcount_max = count;
    1346                 :            : 
    1347                 :            :         md->node[page_to_nid(page)] += nr_pages;
    1348                 :            : }
    1349                 :            : 
    1350                 :            : static struct page *can_gather_numa_stats(pte_t pte, struct vm_area_struct *vma,
    1351                 :            :                 unsigned long addr)
    1352                 :            : {
    1353                 :            :         struct page *page;
    1354                 :            :         int nid;
    1355                 :            : 
    1356                 :            :         if (!pte_present(pte))
    1357                 :            :                 return NULL;
    1358                 :            : 
    1359                 :            :         page = vm_normal_page(vma, addr, pte);
    1360                 :            :         if (!page)
    1361                 :            :                 return NULL;
    1362                 :            : 
    1363                 :            :         if (PageReserved(page))
    1364                 :            :                 return NULL;
    1365                 :            : 
    1366                 :            :         nid = page_to_nid(page);
    1367                 :            :         if (!node_isset(nid, node_states[N_MEMORY]))
    1368                 :            :                 return NULL;
    1369                 :            : 
    1370                 :            :         return page;
    1371                 :            : }
    1372                 :            : 
    1373                 :            : static int gather_pte_stats(pmd_t *pmd, unsigned long addr,
    1374                 :            :                 unsigned long end, struct mm_walk *walk)
    1375                 :            : {
    1376                 :            :         struct numa_maps *md;
    1377                 :            :         spinlock_t *ptl;
    1378                 :            :         pte_t *orig_pte;
    1379                 :            :         pte_t *pte;
    1380                 :            : 
    1381                 :            :         md = walk->private;
    1382                 :            : 
    1383                 :            :         if (pmd_trans_huge_lock(pmd, md->vma, &ptl) == 1) {
    1384                 :            :                 pte_t huge_pte = *(pte_t *)pmd;
    1385                 :            :                 struct page *page;
    1386                 :            : 
    1387                 :            :                 page = can_gather_numa_stats(huge_pte, md->vma, addr);
    1388                 :            :                 if (page)
    1389                 :            :                         gather_stats(page, md, pte_dirty(huge_pte),
    1390                 :            :                                      HPAGE_PMD_SIZE/PAGE_SIZE);
    1391                 :            :                 spin_unlock(ptl);
    1392                 :            :                 return 0;
    1393                 :            :         }
    1394                 :            : 
    1395                 :            :         if (pmd_trans_unstable(pmd))
    1396                 :            :                 return 0;
    1397                 :            :         orig_pte = pte = pte_offset_map_lock(walk->mm, pmd, addr, &ptl);
    1398                 :            :         do {
    1399                 :            :                 struct page *page = can_gather_numa_stats(*pte, md->vma, addr);
    1400                 :            :                 if (!page)
    1401                 :            :                         continue;
    1402                 :            :                 gather_stats(page, md, pte_dirty(*pte), 1);
    1403                 :            : 
    1404                 :            :         } while (pte++, addr += PAGE_SIZE, addr != end);
    1405                 :            :         pte_unmap_unlock(orig_pte, ptl);
    1406                 :            :         return 0;
    1407                 :            : }
    1408                 :            : #ifdef CONFIG_HUGETLB_PAGE
    1409                 :            : static int gather_hugetbl_stats(pte_t *pte, unsigned long hmask,
    1410                 :            :                 unsigned long addr, unsigned long end, struct mm_walk *walk)
    1411                 :            : {
    1412                 :            :         struct numa_maps *md;
    1413                 :            :         struct page *page;
    1414                 :            : 
    1415                 :            :         if (pte_none(*pte))
    1416                 :            :                 return 0;
    1417                 :            : 
    1418                 :            :         page = pte_page(*pte);
    1419                 :            :         if (!page)
    1420                 :            :                 return 0;
    1421                 :            : 
    1422                 :            :         md = walk->private;
    1423                 :            :         gather_stats(page, md, pte_dirty(*pte), 1);
    1424                 :            :         return 0;
    1425                 :            : }
    1426                 :            : 
    1427                 :            : #else
    1428                 :            : static int gather_hugetbl_stats(pte_t *pte, unsigned long hmask,
    1429                 :            :                 unsigned long addr, unsigned long end, struct mm_walk *walk)
    1430                 :            : {
    1431                 :            :         return 0;
    1432                 :            : }
    1433                 :            : #endif
    1434                 :            : 
    1435                 :            : /*
    1436                 :            :  * Display pages allocated per node and memory policy via /proc.
    1437                 :            :  */
    1438                 :            : static int show_numa_map(struct seq_file *m, void *v, int is_pid)
    1439                 :            : {
    1440                 :            :         struct numa_maps_private *numa_priv = m->private;
    1441                 :            :         struct proc_maps_private *proc_priv = &numa_priv->proc_maps;
    1442                 :            :         struct vm_area_struct *vma = v;
    1443                 :            :         struct numa_maps *md = &numa_priv->md;
    1444                 :            :         struct file *file = vma->vm_file;
    1445                 :            :         struct task_struct *task = proc_priv->task;
    1446                 :            :         struct mm_struct *mm = vma->vm_mm;
    1447                 :            :         struct mm_walk walk = {};
    1448                 :            :         struct mempolicy *pol;
    1449                 :            :         char buffer[64];
    1450                 :            :         int nid;
    1451                 :            : 
    1452                 :            :         if (!mm)
    1453                 :            :                 return 0;
    1454                 :            : 
    1455                 :            :         /* Ensure we start with an empty set of numa_maps statistics. */
    1456                 :            :         memset(md, 0, sizeof(*md));
    1457                 :            : 
    1458                 :            :         md->vma = vma;
    1459                 :            : 
    1460                 :            :         walk.hugetlb_entry = gather_hugetbl_stats;
    1461                 :            :         walk.pmd_entry = gather_pte_stats;
    1462                 :            :         walk.private = md;
    1463                 :            :         walk.mm = mm;
    1464                 :            : 
    1465                 :            :         pol = get_vma_policy(task, vma, vma->vm_start);
    1466                 :            :         mpol_to_str(buffer, sizeof(buffer), pol);
    1467                 :            :         mpol_cond_put(pol);
    1468                 :            : 
    1469                 :            :         seq_printf(m, "%08lx %s", vma->vm_start, buffer);
    1470                 :            : 
    1471                 :            :         if (file) {
    1472                 :            :                 seq_printf(m, " file=");
    1473                 :            :                 seq_path(m, &file->f_path, "\n\t= ");
    1474                 :            :         } else if (vma->vm_start <= mm->brk && vma->vm_end >= mm->start_brk) {
    1475                 :            :                 seq_printf(m, " heap");
    1476                 :            :         } else {
    1477                 :            :                 pid_t tid = vm_is_stack(task, vma, is_pid);
    1478                 :            :                 if (tid != 0) {
    1479                 :            :                         /*
    1480                 :            :                          * Thread stack in /proc/PID/task/TID/maps or
    1481                 :            :                          * the main process stack.
    1482                 :            :                          */
    1483                 :            :                         if (!is_pid || (vma->vm_start <= mm->start_stack &&
    1484                 :            :                             vma->vm_end >= mm->start_stack))
    1485                 :            :                                 seq_printf(m, " stack");
    1486                 :            :                         else
    1487                 :            :                                 seq_printf(m, " stack:%d", tid);
    1488                 :            :                 }
    1489                 :            :         }
    1490                 :            : 
    1491                 :            :         if (is_vm_hugetlb_page(vma))
    1492                 :            :                 seq_printf(m, " huge");
    1493                 :            : 
    1494                 :            :         walk_page_range(vma->vm_start, vma->vm_end, &walk);
    1495                 :            : 
    1496                 :            :         if (!md->pages)
    1497                 :            :                 goto out;
    1498                 :            : 
    1499                 :            :         if (md->anon)
    1500                 :            :                 seq_printf(m, " anon=%lu", md->anon);
    1501                 :            : 
    1502                 :            :         if (md->dirty)
    1503                 :            :                 seq_printf(m, " dirty=%lu", md->dirty);
    1504                 :            : 
    1505                 :            :         if (md->pages != md->anon && md->pages != md->dirty)
    1506                 :            :                 seq_printf(m, " mapped=%lu", md->pages);
    1507                 :            : 
    1508                 :            :         if (md->mapcount_max > 1)
    1509                 :            :                 seq_printf(m, " mapmax=%lu", md->mapcount_max);
    1510                 :            : 
    1511                 :            :         if (md->swapcache)
    1512                 :            :                 seq_printf(m, " swapcache=%lu", md->swapcache);
    1513                 :            : 
    1514                 :            :         if (md->active < md->pages && !is_vm_hugetlb_page(vma))
    1515                 :            :                 seq_printf(m, " active=%lu", md->active);
    1516                 :            : 
    1517                 :            :         if (md->writeback)
    1518                 :            :                 seq_printf(m, " writeback=%lu", md->writeback);
    1519                 :            : 
    1520                 :            :         for_each_node_state(nid, N_MEMORY)
    1521                 :            :                 if (md->node[nid])
    1522                 :            :                         seq_printf(m, " N%d=%lu", nid, md->node[nid]);
    1523                 :            : out:
    1524                 :            :         seq_putc(m, '\n');
    1525                 :            : 
    1526                 :            :         if (m->count < m->size)
    1527                 :            :                 m->version = (vma != proc_priv->tail_vma) ? vma->vm_start : 0;
    1528                 :            :         return 0;
    1529                 :            : }
    1530                 :            : 
    1531                 :            : static int show_pid_numa_map(struct seq_file *m, void *v)
    1532                 :            : {
    1533                 :            :         return show_numa_map(m, v, 1);
    1534                 :            : }
    1535                 :            : 
    1536                 :            : static int show_tid_numa_map(struct seq_file *m, void *v)
    1537                 :            : {
    1538                 :            :         return show_numa_map(m, v, 0);
    1539                 :            : }
    1540                 :            : 
    1541                 :            : static const struct seq_operations proc_pid_numa_maps_op = {
    1542                 :            :         .start  = m_start,
    1543                 :            :         .next   = m_next,
    1544                 :            :         .stop   = m_stop,
    1545                 :            :         .show   = show_pid_numa_map,
    1546                 :            : };
    1547                 :            : 
    1548                 :            : static const struct seq_operations proc_tid_numa_maps_op = {
    1549                 :            :         .start  = m_start,
    1550                 :            :         .next   = m_next,
    1551                 :            :         .stop   = m_stop,
    1552                 :            :         .show   = show_tid_numa_map,
    1553                 :            : };
    1554                 :            : 
    1555                 :            : static int numa_maps_open(struct inode *inode, struct file *file,
    1556                 :            :                           const struct seq_operations *ops)
    1557                 :            : {
    1558                 :            :         struct numa_maps_private *priv;
    1559                 :            :         int ret = -ENOMEM;
    1560                 :            :         priv = kzalloc(sizeof(*priv), GFP_KERNEL);
    1561                 :            :         if (priv) {
    1562                 :            :                 priv->proc_maps.pid = proc_pid(inode);
    1563                 :            :                 ret = seq_open(file, ops);
    1564                 :            :                 if (!ret) {
    1565                 :            :                         struct seq_file *m = file->private_data;
    1566                 :            :                         m->private = priv;
    1567                 :            :                 } else {
    1568                 :            :                         kfree(priv);
    1569                 :            :                 }
    1570                 :            :         }
    1571                 :            :         return ret;
    1572                 :            : }
    1573                 :            : 
    1574                 :            : static int pid_numa_maps_open(struct inode *inode, struct file *file)
    1575                 :            : {
    1576                 :            :         return numa_maps_open(inode, file, &proc_pid_numa_maps_op);
    1577                 :            : }
    1578                 :            : 
    1579                 :            : static int tid_numa_maps_open(struct inode *inode, struct file *file)
    1580                 :            : {
    1581                 :            :         return numa_maps_open(inode, file, &proc_tid_numa_maps_op);
    1582                 :            : }
    1583                 :            : 
    1584                 :            : const struct file_operations proc_pid_numa_maps_operations = {
    1585                 :            :         .open           = pid_numa_maps_open,
    1586                 :            :         .read           = seq_read,
    1587                 :            :         .llseek         = seq_lseek,
    1588                 :            :         .release        = seq_release_private,
    1589                 :            : };
    1590                 :            : 
    1591                 :            : const struct file_operations proc_tid_numa_maps_operations = {
    1592                 :            :         .open           = tid_numa_maps_open,
    1593                 :            :         .read           = seq_read,
    1594                 :            :         .llseek         = seq_lseek,
    1595                 :            :         .release        = seq_release_private,
    1596                 :            : };
    1597                 :            : #endif /* CONFIG_NUMA */

Generated by: LCOV version 1.9