| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 1 | #!/usr/bin/env python | 
|  | 2 |  | 
|  | 3 | # This tool lists processes that lock memory pages from swapping to disk. | 
|  | 4 |  | 
|  | 5 | import re | 
| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 6 |  | 
|  | 7 | import psutil | 
|  | 8 |  | 
|  | 9 |  | 
| Dirk Mueller | 02f9e8b | 2017-09-10 02:51:10 +0200 | [diff] [blame] | 10 | LCK_SUMMARY_REGEX = re.compile( | 
|  | 11 | "^VmLck:\s+(?P<locked>[\d]+)\s+kB", re.MULTILINE) | 
| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 12 |  | 
|  | 13 |  | 
|  | 14 | def main(): | 
|  | 15 | try: | 
| Ian Wienand | 9573edb | 2017-03-28 19:37:39 +1100 | [diff] [blame] | 16 | print(_get_report()) | 
| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 17 | except Exception as e: | 
| Ian Wienand | 9573edb | 2017-03-28 19:37:39 +1100 | [diff] [blame] | 18 | print("Failure listing processes locking memory: %s" % str(e)) | 
|  | 19 | raise | 
| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 20 |  | 
|  | 21 |  | 
|  | 22 | def _get_report(): | 
|  | 23 | mlock_users = [] | 
|  | 24 | for proc in psutil.process_iter(): | 
| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 25 | # sadly psutil does not expose locked pages info, that's why we | 
| Dirk Mueller | 02f9e8b | 2017-09-10 02:51:10 +0200 | [diff] [blame] | 26 | # iterate over the /proc/%pid/status files manually | 
| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 27 | try: | 
| Dirk Mueller | 02f9e8b | 2017-09-10 02:51:10 +0200 | [diff] [blame] | 28 | s = open("%s/%d/status" % (psutil.PROCFS_PATH, proc.pid), 'r') | 
|  | 29 | except EnvironmentError: | 
|  | 30 | continue | 
|  | 31 | with s: | 
|  | 32 | for line in s: | 
|  | 33 | result = LCK_SUMMARY_REGEX.search(line) | 
|  | 34 | if result: | 
|  | 35 | locked = int(result.group('locked')) | 
|  | 36 | if locked: | 
|  | 37 | mlock_users.append({'name': proc.name(), | 
|  | 38 | 'pid': proc.pid, | 
|  | 39 | 'locked': locked}) | 
| Ihar Hrachyshka | 2b4735f | 2017-02-10 06:17:37 +0000 | [diff] [blame] | 40 |  | 
|  | 41 | # produce a single line log message with per process mlock stats | 
|  | 42 | if mlock_users: | 
|  | 43 | return "; ".join( | 
|  | 44 | "[%(name)s (pid:%(pid)s)]=%(locked)dKB" % args | 
|  | 45 | # log heavy users first | 
|  | 46 | for args in sorted(mlock_users, key=lambda d: d['locked']) | 
|  | 47 | ) | 
|  | 48 | else: | 
|  | 49 | return "no locked memory" | 
|  | 50 |  | 
|  | 51 |  | 
|  | 52 | if __name__ == "__main__": | 
|  | 53 | main() |