from collections import defaultdict

from system_monitor.msg import Cpu as CpuMsg

_prev_total = defaultdict(int)
_prev_busy = defaultdict(int)


def collect_all():
    """
    parse /proc/stat and calculate total and busy time

    (more specific USER_HZ see man 5 proc for further information )
    """
    msgs = []
    timings, running_processes = _get_cpu_stats()

    for cpu, timings in timings.items():
        cpu_total = sum(timings)
        del timings[3:5]
        cpu_busy = sum(timings)
        cpu_usage = _calculate_usage(cpu, cpu_total, cpu_busy)

        msgs.append(CpuMsg(
            cpu_name=cpu,
            cpu_usage=cpu_usage
        ))

    return running_processes, msgs


def _get_cpu_stats():
    """
    read and parse /proc/stat
    :returns Tuple[timings, open_processes]
    """
    timings = {}
    processes = -1
    with open('/proc/stat', 'r') as file_obj:
        for line in file_obj:
            # only evaluate lines like cpu0, cpu1, cpu2, ...
            if line.startswith('cpu') and line.strip().split()[0] != 'cpu':
                line = line.strip().split()
                timings[line[0]] = [int(x) for x in line[1:]]

            elif line.startswith('procs_running'):
                processes = int(line.strip().split()[1])

    return timings, processes


def _calculate_usage( cpu, total, busy):
    """
    calculate usage
    """
    diff_total = total - _prev_total[cpu]
    diff_busy = busy - _prev_busy[cpu]

    _prev_total[cpu] = total
    _prev_busy[cpu] = busy

    if diff_total == 0:
        return 0
    else:
        return int(diff_busy / diff_total * 100)

@@ -28,16 +28,30 @@
 aultdict
+%0Aimport psutil
 %0A%0Afrom s
@@ -329,25 +329,16 @@
 = %5B%5D%0A   
- timings,
  running
@@ -349,16 +349,49 @@
 cesses =
+ len(psutil.pids())%0A    timings =
  _get_cp
@@ -808,38 +808,67 @@
 rns 
-Tuple%5B
 timings
-, open_processes%5D
+ which contains accumulative busy and total cpu time
 %0A   
@@ -893,27 +893,8 @@
  %7B%7D%0A
-    processes = -1%0A
     
@@ -1213,117 +1213,8 @@
 %5D%5D%0A%0A
-            elif line.startswith('procs_running'):%0A                processes = int(line.strip().split()%5B1%5D)%0A%0A
     
@@ -1231,19 +1231,8 @@
 ings
-, processes
 %0A%0A%0Ad
@@ -1251,20 +1251,23 @@
 e_usage(
- 
 cpu
+_num
 , total,
@@ -1297,24 +1297,60 @@
 culate usage
+ percentage based on busy/total time
 %0A    %22%22%22%0A   
@@ -1386,16 +1386,20 @@
 otal%5Bcpu
+_num
 %5D%0A    di
@@ -1429,16 +1429,20 @@
 busy%5Bcpu
+_num
 %5D%0A%0A    _
@@ -1451,24 +1451,28 @@
 ev_total%5Bcpu
+_num
 %5D = total%0A  
@@ -1487,16 +1487,20 @@
 busy%5Bcpu
+_num
 %5D = busy

fix number of running processes