Quellcodebibliothek Statistik Leitseite products/sources/formale Sprachen/C/Linux/tools/perf/scripts/python/   (Open Source Betriebssystem Version 6.17.9©)  Datei vom 24.10.2025 mit Größe 7 kB image not shown  

Quelle  compaction-times.py   Sprache: Python

 
# report time spent in compaction
# Licensed under the terms of the GNU GPL License version 2

# testing:
# 'echo 1 > /proc/sys/vm/compact_memory' to force compaction of all zones

import os
import sys
import re

import signal
signal.signal(signal.SIGPIPE, signal.SIG_DFL)

usage = "usage: perf script report compaction-times.py -- [-h] [-u] [-p|-pv] [-t | [-m] [-fs] [-ms]] [pid|pid-range|comm-regex]\n"

class popt:
 DISP_DFL = 0
 DISP_PROC = 1
 DISP_PROC_VERBOSE=2

class topt:
 DISP_TIME = 0
 DISP_MIG = 1
 DISP_ISOLFREE = 2
 DISP_ISOLMIG = 4
 DISP_ALL = 7

class comm_filter:
 def __init__(self, re):
  self.re = re

 def filter(self, pid, comm):
  m = self.re.search(comm)
  return m == None or m.group() == ""

class pid_filter:
 def __init__(self, low, high):
  self.low = (0 if low == "" else int(low))
  self.high = (0 if high == "" else int(high))

 def filter(self, pid, comm):
  return not (pid >= self.low and (self.high == 0 or pid <= self.high))

def set_type(t):
 global opt_disp
 opt_disp = (t if opt_disp == topt.DISP_ALL else opt_disp|t)

def ns(sec, nsec):
 return (sec * 1000000000) + nsec

def time(ns):
 return "%dns" % ns if opt_ns else "%dus" % (round(ns, -3) / 1000)

class pair:
 def __init__(self, aval, bval, alabel = None, blabel = None):
  self.alabel = alabel
  self.blabel = blabel
  self.aval = aval
  self.bval = bval

 def __add__(self, rhs):
  self.aval += rhs.aval
  self.bval += rhs.bval
  return self

 def __str__(self):
  return "%s=%d %s=%d" % (self.alabel, self.aval, self.blabel, self.bval)

class cnode:
 def __init__(self, ns):
  self.ns = ns
  self.migrated = pair(0, 0, "moved""failed")
  self.fscan = pair(0,0, "scanned""isolated")
  self.mscan = pair(0,0, "scanned""isolated")

 def __add__(self, rhs):
  self.ns += rhs.ns
  self.migrated += rhs.migrated
  self.fscan += rhs.fscan
  self.mscan += rhs.mscan
  return self

 def __str__(self):
  prev = 0
  s = "%s " % time(self.ns)
  if (opt_disp & topt.DISP_MIG):
   s += "migration: %s" % self.migrated
   prev = 1
  if (opt_disp & topt.DISP_ISOLFREE):
   s += "%sfree_scanner: %s" % (" " if prev else "", self.fscan)
   prev = 1
  if (opt_disp & topt.DISP_ISOLMIG):
   s += "%smigration_scanner: %s" % (" " if prev else "", self.mscan)
  return s

 def complete(self, secs, nsecs):
  self.ns = ns(secs, nsecs) - self.ns

 def increment(self, migrated, fscan, mscan):
  if (migrated != None):
   self.migrated += migrated
  if (fscan != None):
   self.fscan += fscan
  if (mscan != None):
   self.mscan += mscan


class chead:
 heads = {}
 val = cnode(0);
 fobj = None

 @classmethod
 def add_filter(cls, filter):
  cls.fobj = filter

 @classmethod
 def create_pending(cls, pid, comm, start_secs, start_nsecs):
  filtered = 0
  try:
   head = cls.heads[pid]
   filtered = head.is_filtered()
  except KeyError:
   if cls.fobj != None:
    filtered = cls.fobj.filter(pid, comm)
   head = cls.heads[pid] = chead(comm, pid, filtered)

  if not filtered:
   head.mark_pending(start_secs, start_nsecs)

 @classmethod
 def increment_pending(cls, pid, migrated, fscan, mscan):
  head = cls.heads[pid]
  if not head.is_filtered():
   if head.is_pending():
    head.do_increment(migrated, fscan, mscan)
   else:
    sys.stderr.write("missing start compaction event for pid %d\n" % pid)

 @classmethod
 def complete_pending(cls, pid, secs, nsecs):
  head = cls.heads[pid]
  if not head.is_filtered():
   if head.is_pending():
    head.make_complete(secs, nsecs)
   else:
    sys.stderr.write("missing start compaction event for pid %d\n" % pid)

 @classmethod
 def gen(cls):
  if opt_proc != popt.DISP_DFL:
   for i in cls.heads:
    yield cls.heads[i]

 @classmethod
 def str(cls):
  return cls.val

 def __init__(self, comm, pid, filtered):
  self.comm = comm
  self.pid = pid
  self.val = cnode(0)
  self.pending = None
  self.filtered = filtered
  self.list = []

 def __add__(self, rhs):
  self.ns += rhs.ns
  self.val += rhs.val
  return self

 def mark_pending(self, secs, nsecs):
  self.pending = cnode(ns(secs, nsecs))

 def do_increment(self, migrated, fscan, mscan):
  self.pending.increment(migrated, fscan, mscan)

 def make_complete(self, secs, nsecs):
  self.pending.complete(secs, nsecs)
  chead.val += self.pending

  if opt_proc != popt.DISP_DFL:
   self.val += self.pending

   if opt_proc == popt.DISP_PROC_VERBOSE:
    self.list.append(self.pending)
  self.pending = None

 def enumerate(self):
  if opt_proc == popt.DISP_PROC_VERBOSE and not self.is_filtered():
   for i, pelem in enumerate(self.list):
    sys.stdout.write("%d[%s].%d: %s\n" % (self.pid, self.comm, i+1, pelem))

 def is_pending(self):
  return self.pending != None

 def is_filtered(self):
  return self.filtered

 def display(self):
  if not self.is_filtered():
   sys.stdout.write("%d[%s]: %s\n" % (self.pid, self.comm, self.val))


def trace_end():
 sys.stdout.write("total: %s\n" % chead.str())
 for i in chead.gen():
  i.display(),
  i.enumerate()

def compaction__mm_compaction_migratepages(event_name, context, common_cpu,
 common_secs, common_nsecs, common_pid, common_comm,
 common_callchain, nr_migrated, nr_failed):

 chead.increment_pending(common_pid,
  pair(nr_migrated, nr_failed), NoneNone)

def compaction__mm_compaction_isolate_freepages(event_name, context, common_cpu,
 common_secs, common_nsecs, common_pid, common_comm,
 common_callchain, start_pfn, end_pfn, nr_scanned, nr_taken):

 chead.increment_pending(common_pid,
  None, pair(nr_scanned, nr_taken), None)

def compaction__mm_compaction_isolate_migratepages(event_name, context, common_cpu,
 common_secs, common_nsecs, common_pid, common_comm,
 common_callchain, start_pfn, end_pfn, nr_scanned, nr_taken):

 chead.increment_pending(common_pid,
  NoneNone, pair(nr_scanned, nr_taken))

def compaction__mm_compaction_end(event_name, context, common_cpu,
 common_secs, common_nsecs, common_pid, common_comm,
 common_callchain, zone_start, migrate_start, free_start, zone_end,
 sync, status):

 chead.complete_pending(common_pid, common_secs, common_nsecs)

def compaction__mm_compaction_begin(event_name, context, common_cpu,
 common_secs, common_nsecs, common_pid, common_comm,
 common_callchain, zone_start, migrate_start, free_start, zone_end,
 sync):

 chead.create_pending(common_pid, common_comm, common_secs, common_nsecs)

def pr_help():
 global usage

 sys.stdout.write(usage)
 sys.stdout.write("\n")
 sys.stdout.write("-h display this help\n")
 sys.stdout.write("-p display by process\n")
 sys.stdout.write("-pv display by process (verbose)\n")
 sys.stdout.write("-t display stall times only\n")
 sys.stdout.write("-m display stats for migration\n")
 sys.stdout.write("-fs display stats for free scanner\n")
 sys.stdout.write("-ms display stats for migration scanner\n")
 sys.stdout.write("-u display results in microseconds (default nanoseconds)\n")


comm_re = None
pid_re = None
pid_regex = r"^(\d*)-(\d*)$|^(\d*)$"

opt_proc = popt.DISP_DFL
opt_disp = topt.DISP_ALL

opt_ns = True

argc = len(sys.argv) - 1
if argc >= 1:
 pid_re = re.compile(pid_regex)

 for i, opt in enumerate(sys.argv[1:]):
  if opt[0] == "-":
   if opt == "-h":
    pr_help()
    exit(0);
   elif opt == "-p":
    opt_proc = popt.DISP_PROC
   elif opt == "-pv":
    opt_proc = popt.DISP_PROC_VERBOSE
   elif opt == '-u':
    opt_ns = False
   elif opt == "-t":
    set_type(topt.DISP_TIME)
   elif opt == "-m":
    set_type(topt.DISP_MIG)
   elif opt == "-fs":
    set_type(topt.DISP_ISOLFREE)
   elif opt == "-ms":
    set_type(topt.DISP_ISOLMIG)
   else:
    sys.exit(usage)

  elif i == argc - 1:
   m = pid_re.search(opt)
   if m != None and m.group() != "":
    if m.group(3) != None:
     f = pid_filter(m.group(3), m.group(3))
    else:
     f = pid_filter(m.group(1), m.group(2))
   else:
    try:
     comm_re=re.compile(opt)
    except:
     sys.stderr.write("invalid regex '%s'" % opt)
     sys.exit(usage)
    f = comm_filter(comm_re)

   chead.add_filter(f)

Messung V0.5
C=99 H=95 G=96

¤ Dauer der Verarbeitung: 0.11 Sekunden  (vorverarbeitet)  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

Beweissystem der NASA

Beweissystem Isabelle

NIST Cobol Testsuite

Cephes Mathematical Library

Wiener Entwicklungsmethode

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.