fd33abe3f4
In Python 3 print is a function. Especially for multiple string print, need to import print_function from __future__. Story: 2002909 Task: 24560 Signed-off-by: zhangyangyang <zhangyangyang@unionpay.com> Change-Id: Ie31eb59368af57776eb9785dba494432111cd250
122 lines
4.2 KiB
Python
122 lines
4.2 KiB
Python
#!/usr/bin/env python
|
|
# vim: tabstop=4 expandtab shiftwidth=4 softtabstop=4 textwidth=79 autoindent
|
|
|
|
"""
|
|
Python source code
|
|
Last modified: 15 Feb 2014 - 13:38
|
|
Last author: lmwangi at gmail com
|
|
Displays the available memory fragments
|
|
by querying /proc/buddyinfo
|
|
Example:
|
|
# python buddyinfo.py
|
|
"""
|
|
import optparse
|
|
import os
|
|
import re
|
|
from collections import defaultdict
|
|
import logging
|
|
|
|
|
|
class Logger:
|
|
def __init__(self, log_level):
|
|
self.log_level = log_level
|
|
|
|
def get_formatter(self):
|
|
return logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
|
|
|
|
def get_handler(self):
|
|
return logging.StreamHandler()
|
|
|
|
def get_logger(self):
|
|
"""Returns a Logger instance for the specified module_name"""
|
|
logger = logging.getLogger('main')
|
|
logger.setLevel(self.log_level)
|
|
log_handler = self.get_handler()
|
|
log_handler.setFormatter(self.get_formatter())
|
|
logger.addHandler(log_handler)
|
|
return logger
|
|
|
|
|
|
class BuddyInfo(object):
|
|
"""BuddyInfo DAO"""
|
|
def __init__(self, logger):
|
|
super(BuddyInfo, self).__init__()
|
|
self.log = logger
|
|
self.buddyinfo = self.load_buddyinfo()
|
|
|
|
def parse_line(self, line):
|
|
line = line.strip()
|
|
self.log.debug("Parsing line: %s" % line)
|
|
parsed_line = re.match("Node\s+(?P<numa_node>\d+).*zone\s+(?P<zone>\w+)\s+(?P<nr_free>.*)", line).groupdict()
|
|
self.log.debug("Parsed line: %s" % parsed_line)
|
|
return parsed_line
|
|
|
|
def read_buddyinfo(self):
|
|
buddyhash = defaultdict(list)
|
|
buddyinfo = open("/proc/buddyinfo").readlines()
|
|
for line in map(self.parse_line, buddyinfo):
|
|
numa_node = int(line["numa_node"])
|
|
zone = line["zone"]
|
|
free_fragments = map(int, line["nr_free"].split())
|
|
max_order = len(free_fragments)
|
|
fragment_sizes = self.get_order_sizes(max_order)
|
|
usage_in_bytes = [block[0] * block[1] for block in zip(free_fragments, fragment_sizes)]
|
|
buddyhash[numa_node].append({
|
|
"zone": zone,
|
|
"nr_free": free_fragments,
|
|
"sz_fragment": fragment_sizes,
|
|
"usage": usage_in_bytes })
|
|
return buddyhash
|
|
|
|
def load_buddyinfo(self):
|
|
buddyhash = self.read_buddyinfo()
|
|
self.log.info(buddyhash)
|
|
return buddyhash
|
|
|
|
def page_size(self):
|
|
return os.sysconf("SC_PAGE_SIZE")
|
|
|
|
def get_order_sizes(self, max_order):
|
|
return [self.page_size() * 2**order for order in range(0, max_order)]
|
|
|
|
def __str__(self):
|
|
ret_string = ""
|
|
width = 20
|
|
for node in self.buddyinfo:
|
|
ret_string += "Node: %s\n" % node
|
|
for zoneinfo in self.buddyinfo.get(node):
|
|
ret_string += " Zone: %s\n" % zoneinfo.get("zone")
|
|
ret_string += " Free KiB in zone: %.2f\n" % (sum(zoneinfo.get("usage")) / (1024.0))
|
|
ret_string += '\t{0:{align}{width}} {1:{align}{width}} {2:{align}{width}}\n'.format(
|
|
"Fragment size", "Free fragments", "Total available KiB",
|
|
width=width,
|
|
align="<")
|
|
for idx in range(len(zoneinfo.get("sz_fragment"))):
|
|
ret_string += '\t{order:{align}{width}} {nr:{align}{width}} {usage:{align}{width}}\n'.format(
|
|
width=width,
|
|
align="<",
|
|
order = zoneinfo.get("sz_fragment")[idx],
|
|
nr = zoneinfo.get("nr_free")[idx],
|
|
usage = zoneinfo.get("usage")[idx] / 1024.0)
|
|
|
|
return ret_string
|
|
|
|
def main():
|
|
"""Main function. Called when this file is a shell script"""
|
|
usage = "usage: %prog [options]"
|
|
parser = optparse.OptionParser(usage)
|
|
parser.add_option("-s", "--size", dest="size", choices=["B","K","M"],
|
|
action="store", type="choice", help="Return results in bytes, kib, mib")
|
|
|
|
(options, args) = parser.parse_args()
|
|
logger = Logger(logging.DEBUG).get_logger()
|
|
logger.info("Starting....")
|
|
logger.info("Parsed options: %s" % options)
|
|
print(logger)
|
|
buddy = BuddyInfo(logger)
|
|
print(buddy)
|
|
|
|
if __name__ == '__main__':
|
|
main()
|
|
|