Projet

Général

Profil

Paste
Télécharger au format
Statistiques
| Branche: | Révision:

root / plugins / libvirt / kvm_cpu @ acdaeb6d

Historique | Voir | Annoter | Télécharger (3,22 ko)

1
#!/usr/bin/env python3
2
"""
3
=encoding utf8
4

    
5
=head1 NAME
6

    
7
kvm_cpu - show CPU usage of VM
8

    
9

    
10
=head1 CONFIGURATION
11

    
12
Parsed environment variables:
13

    
14
 vmsuffix: part of VM name to be removed
15

    
16

    
17
=head1 LICENSE
18

    
19
GPLv3
20

    
21
SPDX-License-Identifier: GPL-3.0-only
22

    
23

    
24
=head1 AUTHORS
25

    
26
Maxence Dunnewind
27

    
28
Rodolphe Quiédeville
29

    
30

    
31
=head1 MAGIC MARKERS
32

    
33
 #%# capabilities=autoconf
34
 #%# family=contrib
35

    
36
=cut
37
"""
38

    
39
import os
40
import re
41
import sys
42
from subprocess import Popen, PIPE
43

    
44

    
45
def config(vm_names):
46
    ''' Print the plugin's config
47
    @param vm_names : a list of "cleaned" vms' name
48
    '''
49
    percent = 100 * len(
50
        list(filter(lambda x: x[0:3] == 'cpu' and x[3] != ' ', open('/proc/stat', 'r').readlines())))
51

    
52
    base_config = """graph_title KVM Virtual Machine CPU usage
53
graph_vlabel %%
54
graph_category virtualization
55
graph_scale no
56
graph_period second
57
graph_info This graph shows the current CPU used by virtual machines
58
graph_args --base 1000 -r --lower-limit 0 --upper-limit %d""" % percent
59
    print(base_config)
60
    for vm in vm_names:
61
        print("%s_cpu.label %s" % (vm, vm))
62
        print("%s_cpu.min 0" % vm)
63
        print("%s_cpu.type DERIVE" % vm)
64
        print("%s_cpu.draw AREASTACK" % vm)
65
        print("%s_cpu.info percent of cpu time used by virtual machine" % vm)
66

    
67

    
68
def clean_vm_name(vm_name):
69
    ''' Replace all special chars
70
    @param vm_name : a vm's name
71
    @return cleaned vm's name
72
    '''
73
    # suffix part defined in conf
74
    suffix = os.getenv('vmsuffix')
75
    if suffix:
76
        vm_name = re.sub(suffix, '', vm_name)
77
    # proxmox uses kvm with -name parameter
78
    parts = vm_name.split('\x00')
79
    if parts[0].endswith('kvm'):
80
        try:
81
            return parts[parts.index('-name') + 1]
82
        except ValueError:
83
            pass
84
    return re.sub(r"[^a-zA-Z0-9_]", "_", vm_name)
85

    
86

    
87
def detect_kvm():
88
    ''' Check if kvm is installed '''
89
    kvm = Popen("which kvm", shell=True, stdout=PIPE)
90
    kvm.communicate()
91
    return not bool(kvm.returncode)
92

    
93

    
94
def find_vm_names(pids):
95
    '''Find and clean vm names from pids
96
    @return a dictionary of {pids : cleaned vm name}
97
    '''
98
    result = {}
99
    for pid in pids:
100
        cmdline = open("/proc/%s/cmdline" % pid.decode(), "r")
101
        result[pid] = clean_vm_name(
102
            re.sub(r"^.*guest=([a-zA-Z0-9.-_-]*).*$", r"\1", cmdline.readline()))
103
    return result
104

    
105

    
106
def list_pids():
107
    ''' Find the pid of kvm processes
108
    @return a list of pids from running kvm
109
    '''
110
    pid = Popen("pidof qemu-kvm qemu-system-x86_64 kvm", shell=True, stdout=PIPE)
111
    return pid.communicate()[0].split()
112

    
113

    
114
def fetch(vms):
115
    ''' Fetch values for a list of pids
116
    @param dictionary {kvm_pid: cleaned vm name}
117
    '''
118
    for pid, name in vms.items():
119
        user, system = open("/proc/%s/stat" % pid.decode(), 'r').readline().split(' ')[13:15]
120
        print('%s_cpu.value %d' % (name, int(user) + int(system)))
121

    
122

    
123
if __name__ == "__main__":
124
    if len(sys.argv) > 1:
125
        if sys.argv[1] in ['autoconf', 'detect']:
126
            if detect_kvm():
127
                print("yes")
128
            else:
129
                print("no")
130
        elif sys.argv[1] == "config":
131
            config(find_vm_names(list_pids()).values())
132
        else:
133
            fetch(find_vm_names(list_pids()))
134
    else:
135
        fetch(find_vm_names(list_pids()))