#!/usr/bin/python
# Copyright 2018 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Checks kernel tracing events to get the FPS of a CrOS device.

This script requires root privilege to work properly. It may interfere
Chrome tracing because both use ftrace.

Limitation:
It doesn't support multi-screen.
It assumes 60 HZ screen refresh rate.

This script can be used both as a stand alone script or a library.

Sample output (when used as a stand alone script):
    # ./fps_meter.py
    trace method: workq
    [111111111111111111111111111111111111111111111111111111111111] FPS: 60
    [111111111111111111111111111111111111111111111111111111111111] FPS: 60
    [11111111111111111111111111111111111111111111111 111111111111] FPS: 59
    [111111111111111111111111111111111111111111111111111111111111] FPS: 60
    [11111111111111 11111111111111111111 11111111 111111111111111] FPS: 57
    [111111111111111111111111111111111    11111111111111111111111] FPS: 56
    [111   111111111111111111111111111111111111111111111111111111] FPS: 57
     ^
         1 : Frame update count detected in this 1/60 sec interval.

Sample Usage (when used as a library).
    def callback(fps):
        ...

    with FPSMeter(callback) as fps_meter:
        ...

When used as a library, it launches two threads to monitor system FPS rate
periodically. Each time when a FPS rate is sampled, callback() is called with
the FPS number as its parameter.
"""

from __future__ import print_function

import argparse
import atexit
import collections
import common
import functools
import logging
import os
import re
import sys
import threading
import time

from autotest_lib.client.bin import utils as bin_utils
from autotest_lib.client.common_lib import utils as common_lib_utils

TRACE_ROOT = '/sys/kernel/debug/tracing/'
VBLANK_SWITCH = os.path.join(TRACE_ROOT, 'events/drm/drm_vblank_event/enable')
FLIP_SWITCH = os.path.join(TRACE_ROOT, 'events/i915/i915_flip_complete/enable')
WORKQ_SWITCH = os.path.join(
        TRACE_ROOT, 'events/workqueue/workqueue_execute_start/enable')
WORKQ_FILTER = os.path.join(
        TRACE_ROOT, 'events/workqueue/workqueue_execute_start/filter')
TRACE_SWITCH = os.path.join(TRACE_ROOT, 'tracing_on')
TRACE_CLOCK = os.path.join(TRACE_ROOT, 'trace_clock')
TRACE_LOG = os.path.join(TRACE_ROOT, 'trace')
TRACE_PIPE = os.path.join(TRACE_ROOT, 'trace_pipe')
TRACE_MARKER = os.path.join(TRACE_ROOT, 'trace_marker')
REFRESH_RATE = 60
NOTIFY_STRING = 'notify_collection'
STOP_STRING = 'stop_tracing'


def is_intel_gpu():
    """Determines whether it is intel GPU."""
    return os.path.isdir('/sys/bus/pci/drivers/i915')


def get_kernel_version():
    """ Retruns the kernel version in form of xx.xx. """
    m = re.match(r'(\d+\.\d+)\.\d+', bin_utils.get_kernel_version())
    if m:
        return m.group(1)
    return 'unknown'


def get_trace_method():
    """Gets the FPS checking method.

    Checks i915_flip_complete for Intel GPU on Kernel 3.18.
    Checks intel_atomic_commit_work for Intel GPU on Kernel 4.4.
    Checks drm_vblank_event otherwise.
    """
    if is_intel_gpu():
        kernel_version = get_kernel_version()
        if kernel_version == '4.4':
            return 'workq'
        elif kernel_version == '3.18':
            return 'flip'
    # Fallback.
    return 'vblank'


def set_simple_switch(value, filename):
    """ Sets simple switch '1' to the file. """
    orig = common_lib_utils.read_file(filename).strip()
    atexit.register(common_lib_utils.open_write_close, filename, orig)
    common_lib_utils.open_write_close(filename, value)


def set_trace_clock():
    """ Sets trace clock to mono time as chrome tracing in CrOS. """
    PREFERRED_TRACE_CLOCK = 'mono'
    clock = common_lib_utils.read_file(TRACE_CLOCK)
    m = re.match(r'.*\[(\w+)\]', clock)
    if m:
        orig_clock = m.group(1)
        atexit.register(common_lib_utils.open_write_close,
                        TRACE_CLOCK, orig_clock)
    common_lib_utils.open_write_close(TRACE_CLOCK, PREFERRED_TRACE_CLOCK)


def get_kernel_symbol_addr(symbol):
    """ Gets the kernel symple address. Example line in kallsyms:
     ffffffffbc46cb03 T sys_exit
    """
    with open('/proc/kallsyms') as kallsyms:
        for line in kallsyms:
            items = line.split()
            if items[2] == symbol:
                addr = items[0]
                return addr
    return None


def set_workq_filter(function_name):
    """ Sets the workq filter. """
    addr = get_kernel_symbol_addr(function_name)
    if addr:
        filter = 'function == 0x%s' % addr
        common_lib_utils.open_write_close(WORKQ_FILTER, filter)
        # Sets to 0 to remove the filter.
        atexit.register(common_lib_utils.open_write_close, WORKQ_FILTER, '0')


def enable_tracing(trace_method):
    """Enables tracing."""
    if trace_method == 'workq':
        set_simple_switch('1', WORKQ_SWITCH)
        # There are many workqueue_execute_start events,
        # filter to reduce CPU usage.
        set_workq_filter('intel_atomic_commit_work')
    elif trace_method == 'flip':
        set_simple_switch('1', FLIP_SWITCH)
    else:
        set_simple_switch('1', VBLANK_SWITCH)

    set_simple_switch('1', TRACE_SWITCH)
    set_trace_clock()


def get_fps_info(trace_buffer, end_time):
    """ Checks all vblanks in the range [end_time - 1.0, end_time]. """
    frame_info = []
    step = 1.0 / REFRESH_RATE
    step_time = end_time - 1.0 + step
    frame_times = []
    for _ in range(REFRESH_RATE):
        # Checks if there are vblanks in a refresh interval.
        step_count = 0
        while trace_buffer and trace_buffer[0] < step_time:
            frame_times.append(trace_buffer.popleft())
            step_count += 1

        # Each character represent an 1 / REFRESH_RATE interval.
        if step_count:
            if step_count >= 10:
                frame_info.append('*')
            else:
                frame_info.append(str(step_count))
        else:
            frame_info.append(' ')
        step_time += step

    return frame_info, frame_times


def start_thread(function, args=()):
    """ Starts a thread with given argument. """
    new_thread = threading.Thread(target=function, args=args)
    new_thread.start()


class FPSMeter():
    """ Initializes a FPSMeter to measure system FPS periodically. """
    def __init__(self, callback):
        self.is_stopping = threading.Event()
        self.callback = callback


    def __enter__(self):
        self.start()
        return self


    def __exit__(self, type, value, traceback):
        self.stop()


    def notify_collection(self, period_sec=1.0):
        """ Writes a notification mark periodically. """
        logging.info('Notification thread is started')
        next_notify_time = time.time() + period_sec
        while True:
            # Calling time.sleep(1) may suspend for more than 1 second.
            # Sleeps until a specific time to avoid error accumulation.
            sleep_time = next_notify_time - time.time()
            next_notify_time += period_sec
            # Skips if current time is larger than next_notify_time.
            if sleep_time > 0:
                if self.is_stopping.wait(sleep_time):
                    logging.info('Leaving notification thread')
                    # So the main loop doesn't stuck in the readline().
                    common_lib_utils.open_write_close(TRACE_MARKER, STOP_STRING)
                    break
                common_lib_utils.open_write_close(TRACE_MARKER, NOTIFY_STRING)


    def main_loop(self, trace_method):
        """ Main loop to parse the trace.

        There are 2 threads involved:
        Main thread:
            Using blocking read to get data from trace_pipe.
        Notify thread: The main thread may wait indifinitely if there
            is no new trace. Writes to the pipe once per second to avoid
            the indefinite waiting.
        """
        logging.info('Fps meter main thread is started.')

        # Sample trace:
        # <idle>-0  [000] dNh3 631.905961: drm_vblank_event: crtc=0, seq=65496
        # <idle>-0  [000] d.h3 631.922681: drm_vblank_event: crtc=0, seq=65497
        # fps_meter [003] ..1 632.393953: tracing_mark_write: notify_collection
        # ..
        re_notify = re.compile(
                r'.* (\d+\.\d+): tracing_mark_write: ' + NOTIFY_STRING)
        if trace_method == 'workq':
            re_trace = re.compile(
                    r'.* (\d+\.\d+): workqueue_execute_start: '
                    r'work struct ([\da-f]+): '
                    r'function intel_atomic_commit_work')
        elif trace_method == 'flip':
            re_trace = re.compile(
                    r'.* (\d+\.\d+): i915_flip_complete: '
                    r'plane=(\d+), obj=([\da-f]+)')
        else:
            re_trace = re.compile(
                    r'.* (\d+\.\d+): drm_vblank_event: crtc=(\d+), seq=(\d+)')

        trace_buffer = collections.deque()
        with open(TRACE_PIPE) as trace_pipe:
            # The pipe may block a few seconds if using:
            # for line in trace_pipe
            while not self.is_stopping.is_set():
                line = trace_pipe.readline()
                m_trace = re_trace.match(line)
                if m_trace:
                    timestamp = float(m_trace.group(1))
                    trace_buffer.append(timestamp)
                else:
                    m_notify = re_notify.match(line)
                    if m_notify:
                        timestamp = float(m_notify.group(1))
                        self.callback(get_fps_info(trace_buffer, timestamp))
            logging.info('Leaving fps meter main thread')


    def start(self):
        """ Starts the FPS meter by launching needed threads. """
        # The notificaiton thread.
        start_thread(self.notify_collection)

        # The main thread.
        trace_method = get_trace_method()
        enable_tracing(trace_method)
        start_thread(self.main_loop, [trace_method])


    def stop(self):
        """ Stops the FPS meter. Shut down threads. """
        logging.info('Shutting down FPS meter')
        self.is_stopping.set()


def output_fps_info(verbose, fps_info):
    """ Print the fps info to the screen. """
    frame_info, frame_times = fps_info
    fps_count = len([f for f in frame_info if f != ' '])
    frame_info_str = ''.join(frame_info)
    print('[%s] FPS: %2d' % (frame_info_str, fps_count))
    if frame_times and verbose:
        print(', '.join(['%.3f' % t for t in frame_times]))


def main(argv):
    """ Print fps information on the screen. """
    parser = argparse.ArgumentParser(description='Print fps infomation.')
    parser.add_argument('--verbose', action='store_true',
                                        help='print verbose frame time info')
    parser.add_argument('--debug', action='store_true',
                                        help='print debug message')
    options = parser.parse_args()

    if options.debug:
        rootLogger = logging.getLogger()
        rootLogger.setLevel(logging.DEBUG)
        # StreamHandler() defaults to stderr.
        rootLogger.addHandler(logging.StreamHandler())

    print('FPS meter trace method %s' % get_trace_method())
    with FPSMeter(functools.partial(output_fps_info, options.verbose)):
        while True:
            try:
                time.sleep(86400)
            except KeyboardInterrupt:
                print('Exiting...')
                break


if __name__ == '__main__':
    sys.exit(main(sys.argv[1:]))
