1c8b7cb8b69d7563b06e72a1abe9b91ee8e51711aJavi Merino#    Copyright 2015-2016 ARM Limited
2a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh#
394d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# Licensed under the Apache License, Version 2.0 (the "License");
494d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# you may not use this file except in compliance with the License.
594d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# You may obtain a copy of the License at
694d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino#
794d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino#     http://www.apache.org/licenses/LICENSE-2.0
894d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino#
994d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# Unless required by applicable law or agreed to in writing, software
1094d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# distributed under the License is distributed on an "AS IS" BASIS,
1194d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1294d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# See the License for the specific language governing permissions and
1394d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino# limitations under the License.
1494d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino#
1594d913ce019b7787a20441565e19f5cb51e28ea9Javi Merino
16a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh"""Allow the user to assert various conditions
176b48a45842b50e4a50e2db2fd8db63b63e6b69c2Javi Merinobased on the grammar defined in trappy.stats.grammar. The class is
18a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singhalso intended to have aggregator based functionality. This is not
19a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singhimplemented yet.
20a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh"""
21a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
226b48a45842b50e4a50e2db2fd8db63b63e6b69c2Javi Merinofrom trappy.stats.grammar import Parser
23a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singhimport warnings
24a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singhimport numpy as np
255af9d234eb3445a36c34695c5d1b1bd8b88d5c6fJavi Merinoimport pandas as pd
26a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
27a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh# pylint: disable=invalid-name
28a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
298a51ec958a6d3477da3b2385c13c26e367d6034fKapileshwar Singh
308a51ec958a6d3477da3b2385c13c26e367d6034fKapileshwar Singhclass Analyzer(object):
31a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
32a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh    """
337881a53f3898b121e04de245a80f24976ae198b6Javi Merino    :param data: TRAPpy FTrace Object
347881a53f3898b121e04de245a80f24976ae198b6Javi Merino    :type data: :mod:`trappy.ftrace.FTrace`
35e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh
36e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh    :param config: A dictionary of variables, classes
37e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh        and functions that can be used in the statements
38e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh    :type config: dict
39a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh    """
40a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
4101554cc19f301becb9bbd165da7cadc1f57ed5a3Kapileshwar Singh    def __init__(self, data, config, **kwargs):
4201554cc19f301becb9bbd165da7cadc1f57ed5a3Kapileshwar Singh        self._parser = Parser(data, config, **kwargs)
43a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
44d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh    def assertStatement(self, statement, select=None):
45e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh        """Solve the statement for a boolean result
46e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh
47e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh        :param statement: A string representing a valid
48e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh            :mod:`trappy.stats.grammar` statement
49e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh        :type statement: str
50e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh
51e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh        :param select: If the result represents a boolean
52e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh            mask and the data was derived from a TRAPpy event
53e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh            with a pivot value. The :code:`select` can be
54e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh            used to select a particular pivot value
55e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh        :type select: :mod:`pandas.DataFrame` column
56e79171c2d42739d6d80958037137600cf8c7ea6bKapileshwar Singh        """
57a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
58d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh        result = self.getStatement(statement, select=select)
59d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh
605af9d234eb3445a36c34695c5d1b1bd8b88d5c6fJavi Merino        if isinstance(result, pd.DataFrame):
615af9d234eb3445a36c34695c5d1b1bd8b88d5c6fJavi Merino            result = result.all().all()
625af9d234eb3445a36c34695c5d1b1bd8b88d5c6fJavi Merino        elif not(isinstance(result, bool) or isinstance(result, np.bool_)): # pylint: disable=no-member
635af9d234eb3445a36c34695c5d1b1bd8b88d5c6fJavi Merino            warnings.warn("solution of {} is not boolean".format(statement))
645af9d234eb3445a36c34695c5d1b1bd8b88d5c6fJavi Merino
65a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh        return result
66a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
67d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh    def getStatement(self, statement, reference=False, select=None):
68a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh        """Evaluate the statement"""
69a9c8716f5daa25a7c9bb2052bc6c02d2bf11b6cKapileshwar Singh
70d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh        result = self._parser.solve(statement)
71d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh
72d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh        # pylint: disable=no-member
73d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh        if np.isscalar(result):
74d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh            return result
75d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh        # pylint: enable=no-member
76d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh
77d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh        if select is not None and len(result):
78d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh            result = result[select]
79d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh            if reference:
80d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh                result = self._parser.ref(result)
81d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh
82d87e98917a6de153e9e0a79d782b33e1e1465444Kapileshwar Singh        return result
83