# !/usr/bin/env python
###############################################################################
# Copyright (c) 2020-2023, ARM Limited and Contributors. All rights reserved.
#
# SPDX-License-Identifier: BSD-3-Clause
###############################################################################

###############################################################################
# FILE: intermediate_layer.py
#
# DESCRIPTION: Creates an intermediate json file with information provided
#              by the configuration json file, dwarf signatures and trace
#              files.
#
###############################################################################

import os
import re
import glob
import argparse
import subprocess
import json
from argparse import RawTextHelpFormatter
import cc_logger
import time
from typing import Dict
from typing import List
from typing import Generator
from typing import Union
from typing import Tuple
import logging

__version__ = "7.0"

# Static map that defines the elf file source type in the intermediate json
ELF_MAP = {
    "bl1": 0,
    "bl2": 1,
    "bl31": 2,
    "bl32": 3,
    "scp_ram": 10,
    "scp_rom": 11,
    "mcp_rom": 12,
    "mcp_ram": 13,
    "secure_hafnium": 14,
    "hafium": 15,
    "custom_offset": 100
}


def os_command(command, show_command=False):
    """
    Function that execute an os command, on fail exit the program

    :param command: OS command as string
    :param show_command: Optional argument to print the command in stdout
    :return: The string output of the os command
    """
    try:
        if show_command:
            print("OS command: {}".format(command))
        out = subprocess.check_output(
            command, stderr=subprocess.STDOUT, shell=True)
    except subprocess.CalledProcessError as ex:
        raise Exception(
            "Exception running command '{}': {}({})".format(
                command, ex.output, ex.returncode))
    return out.decode("utf8")


def load_stats_from_traces(trace_globs):
    """
    Function to process and consolidate statistics from trace files

    :param trace_globs: List of trace file patterns
    :return: Dictionary with stats from trace files i.e.
        {mem address in decimal}=(times executed, inst size)
    """
    stats = {}
    stat_size = {}

    # Make a list of unique trace files
    trace_files = []
    for tg in trace_globs:
        trace_files.extend(glob.glob(tg))
    trace_files = set(trace_files)

    if not trace_files:
        raise Exception("No trace files found for '{}'".format(trace_globs))
    # Load stats from the trace files
    for trace_file in trace_files:
        try:
            with open(trace_file, 'r') as f:
                for line in f:
                    data = line.split()
                    address = int(data[0], 16)
                    stat = int(data[1])
                    size = int(data[2])
                    stat_size[address] = size
                    if address in stats:
                        stats[address] += stat
                    else:
                        stats[address] = stat
        except Exception as ex:
            logger.error("@Loading stats from trace files:{}".format(ex))
    # Merge the two dicts
    for address in stats:
        stats[address] = (stats[address], stat_size[address])
    return stats


def get_code_sections_for_binary(elf_name):
    """
    Function to return the ranges of memory address for sections of code
    in the elf file

    :param elf_name: Elf binary file name
    :return: List of code sections tuples, i.e. (section type, initial
            address, end address)
    """
    command = """%s -h %s | grep -B 1 CODE | grep -v CODE \
                | awk '{print $2" "$4" "$3}'""" % (OBJDUMP, elf_name)
    text_out = os_command(command)
    sections = text_out.split('\n')
    sections.pop()
    secs = []
    for sec in sections:
        try:
            d = sec.split()
            secs.append((d[0], int(d[1], 16), int(d[2], 16)))
        except Exception as ex:
            logger.error(
                "@Returning memory address code sections:".format(ex))
    return secs


def get_executable_ranges_for_binary(elf_name):
    """
    Get function ranges from an elf file

    :param elf_name: Elf binary file name
    :return: List of tuples for ranges i.e. (range start, range end)
    """
    # Parse all $x / $d symbols
    symbol_table = []
    address = None
    _type = None
    command = r"""%s -s %s | awk '/\$[xatd]/ {print $2" "$8}'""" % (
        READELF, elf_name)
    text_out = os_command(command)
    lines = text_out.split('\n')
    lines.pop()
    for line in lines:
        try:
            data = line.split()
            address = int(data[0], 16)
            _type = 'X' if data[1] in ['$x', '$t', '$a'] else 'D'
        except Exception as ex:
            logger.error("@Getting executable ranges:".format(ex))
        symbol_table.append((address, _type))

    # Add markers for end of code sections
    sections = get_code_sections_for_binary(elf_name)
    for sec in sections:
        symbol_table.append((sec[1] + sec[2], 'S'))

    # Sort by address
    symbol_table = sorted(symbol_table, key=lambda tup: tup[0])

    # Create ranges (list of START/END tuples)
    ranges = []
    range_start = symbol_table[0][0]
    rtype = symbol_table[0][1]
    for sym in symbol_table:
        if sym[1] != rtype:
            if rtype == 'X':
                # Subtract one because the first address of the
                # next range belongs to the next range.
                ranges.append((range_start, sym[0] - 1))
            range_start = sym[0]
            rtype = sym[1]
    return ranges


def remove_workspace(path, workspace):
    """
    Get the relative path to a given workspace

    :param path: Path relative to the workspace to be returned
    :param workspace: Path.
    """
    ret = path if workspace is None else os.path.relpath(path, workspace)
    return ret


def get_function_line_numbers(source_file: str) -> Dict[str, int]:
    """
    Using ctags get all the function names with their line numbers
    within the source_file

    :return: Dictionary with function name as key and line number as value
    """
    command = "ctags -x --c-kinds=f {}".format(source_file)
    fln = {}
    try:
        function_lines = os_command(command).split("\n")
        for line in function_lines:
            cols = line.split()
            if len(cols) < 3:
                continue
            if cols[1] == "function":
                fln[cols[0]] = int(cols[2])
            elif cols[1] == "label":
                if cols[0] == "func":
                    fln[cols[-1]] = int(cols[2])
                elif cols[0] + ":" == cols[-1]:
                    fln[cols[0]] = int(cols[2])
    except BaseException:
        logger.warning("Warning: Can't get all function line numbers from %s" %
                       source_file)
    except Exception as ex:
        logger.warning(f"Warning: Unknown error '{ex}' when executing command "
                       f"'{command}'")
        return {}
    return fln


class FunctionLineNumbers(object):
    """Helper class used to get a function start line number within
     a source code file"""

    def __init__(self, workspace: str):
        """
        Initialise dictionary to allocate source code files with the
        corresponding function start line numbers.

        :param workspace: The folder where the source files are deployed
        """
        self.filenames = {}
        self.workspace = workspace

    def get_line_number(self, filename: str, function_name: str) -> int:
        if not FUNCTION_LINES_ENABLED:
            return 0
        if filename not in self.filenames:
            source_file = os.path.join(self.workspace, filename)
            # Get all functions with their lines in the source file
            self.filenames[filename] = get_function_line_numbers(source_file)
        return 0 if function_name not in self.filenames[filename] else \
            self.filenames[filename][function_name]


class BinaryParser(object):
    """Class used to create an instance to parse the binary files with a
    dwarf signature in order to produce logical information to be matched with
    traces and produce a code coverage report"""

    def __init__(self, dump: str, _workspace: str, _remove_workspace: bool,
                 local_workspace: str):
        """
        Initialisation of the instance to parse binary files.

        :param dump: Binary dump (string) containing assembly code and source
        code metadata, i.e. source code location and line number.
        :param _workspace: Workspace (folder) where the source files were
        built from.
        :param _remove_workspace: Boolean to indicate if the build of
        source files was local (false) or from a CI (true).
        :param local_workspace: Path to the local workspace where the source
        files reside
        """
        self.dump = dump
        self.no_source_functions = self.get_no_source_functions()
        self.workspace = _workspace
        self.remove_workspace = _remove_workspace
        self.local_workspace = local_workspace
        self.function_line_numbers = FunctionLineNumbers(self.local_workspace)

    def get_no_source_functions(self) -> Dict[int, Dict]:
        """Find in the dwarf dump all the functions with no source code i.e.:
        function_name():
               start_hex_address opcode
               ....
               end_hex_address opcode

        :returns: Dictionary of functions indexed by start address function's
        location
        """
        # The functions dict is [start_dec_address]={function name, function
        # end address in decimal}
        _functions = {}
        groups = re.findall(r"(.+?)\(\):\n\s+([a-f0-9]+):."
                            r"+?\n(\s+([a-f0-9]+):.+?\n)*", self.dump)
        for group in groups:
            function_name, start_hex_address, _, end_hex_address = group
            if not end_hex_address:
                end_hex_address = start_hex_address
            _functions[int(start_hex_address, 16)] = {'name': function_name,
                                                      'end_address': int(
                                                          end_hex_address, 16)}
        return _functions

    class SourceCodeBlock(object):
        """Class used to represent a source code block of information within
        a function block in a binary dump file.
        The source code block contains the following components:
        - Source code file that contains the source code corresponding
        to the assembly code.
        - Line number within the source code file corresponding to the source
        code.
        - Assembly code block.
        """

        def __init__(self, source_code_block_dump):
            """
            Create an instance of a source code block within a function block.

            :param source_code_block: Tuple of 3 elements that contains the
            components of a source code block.
            """
            self.source_file, self.line_number, self.asm_code \
                = source_code_block_dump

        @staticmethod
        def get(dwarf_data: str) -> Generator['BinaryParser.SourceCodeBlock',
                                              None, None]:
            source_block_groups = re.findall(r"(?s)(/[a-zA-Z_0-9][^\n]+?):"
                                             r"([0-9]+)(?: [^\n]+)?\n(.+?)"
                                             r"\n(?=/[a-zA-Z_0-9][^\n]+?"
                                             r":[0-9]+[^\n]+?\n|\n$)",
                                             dwarf_data)
            for source_block_group in source_block_groups:
                if len(source_block_group) != 3:
                    logger.warning(f"Source code incomplete:"
                                   f"{source_block_group}")
                    continue
                source_block_dump = list(source_block_group)
                source_block_dump[-1] += "\n\n"  # For parsing assembly lines
                yield BinaryParser.SourceCodeBlock(source_block_dump)

        def __str__(self):
            return f"'{self.source_file}:{self.line_number}'"

    class FunctionBlock(object):
        """Class used to parse and obtain a function block from the
        binary dump file that corresponds to a function declaration in the
        source code file and a block of assembly code mixed with corresponding
        source code lines, i.e. dwarf information.
        The function block has the following components:
        - Function name at source code.
        - DWARF data.
        - Function declaration's line number at source code.
        This comes from dump blocks like these:
        0000000000000230 <_setup>:
        read_el(): <---- Function name at source code
        /home/user/aarch64/setup.c:238 <------ Source file and line number
        230:	d53e1100 	mrs	x0, scr_el3   <----- Assembly lines belonging to
        the source code
        no_setup():
        /home/user/no_setup.c:618
        234:	b2760000 	orr	x0, x0, #0x400
        """

        def __init__(self, function_group: List[str]):
            """
            Create an instance of a function block within a binary dump.

            :param function_group: List containing the function name and
            dwarf data of the block.
            """
            self.name, self.dwarf = function_group
            # Now obtain the function's source file
            m = re.search(r"(/.+?):([0-9]+)(?: [^\n]+)?\n", self.dwarf)
            self.source_file = m.groups()[0].strip() \
                if m and len(m.groups()) == 2 else None
            # Computed later
            self.function_line_number = None

        @staticmethod
        def get(dump: str) -> Generator['BinaryParser.FunctionBlock', None,
                                        None]:
            """
            Static method generator to extract a function block from the binary
            dump.

            :param dump: Binary dump (string) that contains the binary file
            information.
            :return: A FunctionBlock object that is a logical representation
            of a function declaration within the binary dump.
            """
            function_groups = re.findall(r"(?s)([a-zA-Z0-9_]+?)\(\):"
                                         r"\n(/.+?:[0-9]+?.+?)\n"
                                         r"(?=[a-zA-Z0-9_]+?\(\):\n|\n\n$)",
                                         dump)
            for group in function_groups:
                if len(group) != 2:
                    continue
                function_group = list(group)
                function_group[-1] += "\n\n"  # For parsing source code blocks
                yield BinaryParser.FunctionBlock(function_group)

        @property
        def values(self):
            return self.name, self.source_file, self.function_line_number

        def __str__(self):
            return f"'{self.name}:{self.function_line_number}'"

    class AssemblyLine(object):
        """Class used to represent an assembly code line within an
        assembly code block.
        The assembly line instruction is formed by the following components:
        - Hexadecimal address of the assembly instruction.
        - Assembly instruction.
        """

        def __init__(self, line):
            """
            Create an instance representing an assembly code line within an
            assembly code block.

            :param line: Tuple of 2 elements [Hexadecimal number,
            and assembly code]
            """
            self.hex_line_number, self.opcode = line
            self.dec_address = int(self.hex_line_number, 16)
            self.times_executed = 0

        @staticmethod
        def get(asm_code: str) -> Generator['BinaryParser.AssemblyLine',
                                            None, None]:
            """
            Static method generator to extract an assembly code line from an
            assembly code block.

            :param asm_code: Lines of assembly code within the dump
            :return: AssemblyLine object.
            """
            lines = re.findall(r"^(?:\s+)?([a-fA-F0-9]+):\t(.+?)\n", asm_code,
                               re.DOTALL | re.MULTILINE)
            for line in lines:
                if len(line) != 2:
                    logger.warning(f"Assembly code incomplete: {line}")
                    continue
                yield BinaryParser.AssemblyLine(line)

    @staticmethod
    def get_asm_line(source_code_block: 'BinaryParser.SourceCodeBlock',
                     traces_stats) -> \
            Generator['BinaryParser.AssemblyLine', None, None]:
        """Generator method to obtain all assembly line codes within a source
        code line """
        traces_stats = traces_stats
        for asm_line in BinaryParser.AssemblyLine.get(
                source_code_block.asm_code):
            asm_line.times_executed = traces_stats.get(asm_line.dec_address,
                                                       [0])[0]
            yield asm_line

    def get_source_code_block(self, function_block: FunctionBlock) -> \
            Generator['BinaryParser.SourceCodeBlock', None, None]:
        """
        Generator method to obtain all the source code blocks within a
        function block.

        :param function_block: FunctionBlock object that contains the code
        the source code blocks.
        :return: A SourceCodeBlock object.
        """
        for source_code_block in BinaryParser.SourceCodeBlock.get(
                function_block.dwarf):
            if self.remove_workspace:
                source_code_block.source_file = remove_workspace(
                    source_code_block.source_file, self.workspace)
            yield source_code_block

    def get_function_block(self) -> Generator['BinaryParser.FunctionBlock',
                                              None, None]:
        """Generator method to obtain all the function blocks contained in
        the binary dump file.
        """
        for function_block in BinaryParser.FunctionBlock.get(self.dump):
            if function_block.source_file is None:
                logger.warning(f"Source file not found for function "
                               f"{function_block.name}, will not be covered")
                continue
            if self.remove_workspace:
                function_block.source_file = remove_workspace(
                    function_block.source_file, self.workspace)
            function_block.function_line_number = \
                self.function_line_numbers.get_line_number(
                    function_block.source_file, function_block.name)
            yield function_block


class CoverageHandler(object):
    """ Class used to handle source files coverage linked with their functions
    and line code coverage from function blocks obtained from DWARF data and
    trace code coverage from CC plugin"""

    def __init__(self):
        self._source_files = {}

    def add_function_coverage(self, function_data:
                              Union[BinaryParser.FunctionBlock,
                                    Tuple[str, str, int]]):
        """ Add a function coverage block and a source file coverage block,
        if not already created and link them"""
        # Unpack function data either as an FunctionBlock object property or a
        # tuple
        name, source_file, function_line_number = function_data.values if \
            isinstance(function_data, BinaryParser.FunctionBlock) else \
            function_data

        # Add source file coverage block it if not already there
        self._source_files.setdefault(source_file,
                                      {"functions": {}, "lines": {}})
        # Add a function coverage block (if not existent) from a function
        # block using the function block name as key and link it to the source
        # file coverage block
        self._source_files[source_file]["functions"].setdefault(
            name, {"covered": False, "line_number": function_line_number})

    def add_line_coverage(self, source_code_block:
                          BinaryParser.SourceCodeBlock):
        """ Add a line coverage block and a source file coverage block,
        if not already created and link them"""
        # Add source file coverage block it if not already there
        self._source_files.setdefault(source_code_block.source_file,
                                      {"functions": {}, "lines": {}})
        # Add a line coverage block (if not existent) from a source block
        # using the source code line number as a key and link it to the source
        # file coverage block
        self._source_files[source_code_block.source_file]["lines"].setdefault(
            source_code_block.line_number, {"covered": False, "elf_index": {}})

    def add_asm_line(self, source_code_block: BinaryParser.SourceCodeBlock,
                     asm_line: BinaryParser.AssemblyLine, elf_index: int):
        """Add an assembly line from the DWARF data linked to a source code
        line"""
        self._source_files[source_code_block.source_file]["lines"][
            source_code_block.line_number]["elf_index"].setdefault(
            elf_index, {})
        self._source_files[source_code_block.source_file]["lines"][
            source_code_block.line_number]["elf_index"][
            elf_index].setdefault(asm_line.dec_address,
                                  (asm_line.opcode, asm_line.times_executed))

    def set_line_coverage(self, source_code_block:
                          BinaryParser.SourceCodeBlock, value: bool):
        self._source_files[source_code_block.source_file]["lines"][
            source_code_block.line_number]["covered"] = value

    def set_function_coverage(self, function_block:
                              Union[BinaryParser.FunctionBlock,
                                    Tuple[str, str]], value: bool):
        name, source_file = (function_block.name, function_block.source_file)\
            if isinstance(function_block, BinaryParser.FunctionBlock) else \
            function_block
        self._source_files[source_file]["functions"][name]["covered"] = value

    @property
    def source_files(self):
        return self._source_files


class IntermediateCodeCoverage(object):
    """Class used to process the trace data along with the dwarf
    signature files to produce an intermediate layer in json with
    code coverage in assembly and c source code.
    """

    def __init__(self, _config, local_workspace):
        self._data = {}
        self.config = _config
        self.workspace = self.config['parameters']['workspace']
        self.remove_workspace = self.config['configuration']['remove_workspace']
        self.local_workspace = local_workspace
        self.elfs = self.config['elfs']
        # Dictionary with stats from trace files {address}=(times executed,
        # inst size)
        self.traces_stats = {}
        # Dictionary of unique assembly line memory address against source
        # file location
        # {assembly address} = (opcode, source file location, line number in
        # the source file, times executed)
        self.asm_lines = {}
        # Dictionary of {source file location}=>{'lines': {'covered':Boolean,
        # 'elf_index'; {elf index}=>{assembly address}=>(opcode,
        # times executed),
        # 'functions': {function name}=>is covered(boolean)}
        self.coverage = CoverageHandler()
        self.functions = []
        # Unique set of elf list of files
        self.elf_map = {}
        # For elf custom mappings
        self.elf_custom = None

    def process(self):
        """
        Public method to process the trace files and dwarf signatures
        using the information contained in the json configuration file.
        This method writes the intermediate json file output linking
        the trace data and c source and assembly code.
        """
        self.asm_lines = {}
        # Initialize for unknown elf files
        self.elf_custom = ELF_MAP["custom_offset"]
        print("Generating intermediate json layer '{}'...".format(
            self.config['parameters']['output_file']))
        for elf in self.elfs:
            # Gather information
            elf_name = elf['name']
            # Obtain trace data
            self.traces_stats = load_stats_from_traces(elf['traces'])
            # Produce code coverage
            self._process_binary(elf_name)
            # Write to the intermediate json file
        data = {"source_files": self.coverage.source_files,
                "configuration": {
                    "sources": self.config['parameters']['sources'],
                    "metadata": "" if 'metadata' not in
                                      self.config['parameters'] else
                    self.config['parameters']['metadata'],
                    "elf_map": self.elf_map}
                }
        json_data = json.dumps(data, indent=4, sort_keys=True)
        with open(self.config['parameters']['output_file'], "w") as f:
            f.write(json_data)

    def get_elf_index(self, elf_name: str) -> int:
        """Obtains the elf index and fills the elf_map instance variable"""
        if elf_name not in self.elf_map:
            if elf_name in ELF_MAP:
                self.elf_map[elf_name] = ELF_MAP[elf_name]
            else:
                self.elf_map[elf_name] = ELF_MAP["custom_offset"]
                ELF_MAP["custom_offset"] += 1
        return self.elf_map[elf_name]

    def _process_binary(self, elf_filename: str) -> BinaryParser:
        """
        Process an elf file i.e. match the source code and asm lines against
        trace files (coverage).

        :param elf_filename: Elf binary file name
        """
        command = "%s -Sl %s | tee %s" % (OBJDUMP, elf_filename,
                                          elf_filename.replace(".elf", ".dump") \
                                          .replace(".axf",  ".dump"))
        dump = os_command(command, show_command=True)
        dump += "\n\n"  # For pattern matching the last function
        logger.info(f"Parsing assembly file {elf_filename}")
        elf_name = os.path.splitext(os.path.basename(elf_filename))[0]
        elf_index = self.get_elf_index(elf_name)
        parser = BinaryParser(dump, self.workspace, self.remove_workspace,
                              self.local_workspace)
        total_number_functions = 0
        functions_covered = 0
        for function_block in parser.get_function_block():
            total_number_functions += 1
            # Function contains source code
            self.coverage.add_function_coverage(function_block)
            is_function_covered = False
            for source_code_block in parser.get_source_code_block(
                    function_block):
                self.coverage.add_line_coverage(source_code_block)
                is_line_covered = False
                for asm_line in parser.get_asm_line(source_code_block,
                                                    self.traces_stats):
                    # Here it is checked the line coverage
                    is_line_covered = asm_line.times_executed > 0 or \
                                      is_line_covered
                    self.coverage.add_asm_line(source_code_block, asm_line,
                                               elf_index)
                logger.debug(f"Source file {source_code_block} is "
                             f"{'' if is_line_covered else 'not '}covered")
                if is_line_covered:
                    self.coverage.set_line_coverage(source_code_block, True)
                    is_function_covered = True
            logger.debug(f"\tFunction '{function_block.name}' at '"
                         f"{function_block.source_file} is "
                         f"{'' if is_function_covered else 'not '}covered")
            if is_function_covered:
                self.coverage.set_function_coverage(function_block, True)
                functions_covered += 1
        logger.info(f"Total functions: {total_number_functions}, Functions "
                    f"covered:{functions_covered}")
        # Now check code coverage in the functions with no dwarf signature
        self._process_fn_no_sources(parser)
        return parser

    def _process_fn_no_sources(self, parser: BinaryParser):
        """
        Checks function coverage for functions with no dwarf signature i.e.
         sources.

        :param parser: Binary parser that contains objects needed
        to check function line numbers including the dictionary of functions
        to be checked i.e [start_dec_address]={'name', 'end_address'}
        """
        if not FUNCTION_LINES_ENABLED:
            return  # No source code at the workspace
        traces_addresses = sorted(self.traces_stats.keys())
        traces_address_pointer = 0
        _functions = parser.no_source_functions
        functions_addresses = sorted(_functions.keys())
        address_size = 4
        for start_address in functions_addresses:
            function_covered = False
            function_name = _functions[start_address]['name']
            # Get all files in the source code where the function is defined
            source_files = os_command("grep --include '*.c' --include '*.s' "
                                      "--include '*.S' -nrw '{}' {}"
                                      "| cut -d: -f1".
                                      format(function_name,
                                             self.local_workspace))
            unique_files = set(source_files.split())
            sources_found = []
            for source_file in unique_files:
                line_number = parser.function_line_numbers.get_line_number(
                    source_file, function_name)
                if line_number > 0:
                    sources_found.append((source_file, line_number))
            if len(sources_found) == 0:
                logger.debug(f"'{function_name}' not found in sources")
            elif len(sources_found) > 1:
                logger.warning(f"'{function_name}' declared in "
                               f"{len(sources_found)} files")
            else:
                source_file_found, function_line_number = sources_found[0]
                function_source_file = remove_workspace(source_file_found,
                                                        self.local_workspace)
                self.coverage.add_function_coverage((function_name,
                                                     function_source_file,
                                                     function_line_number))
                for in_function_address in \
                        range(start_address,
                              _functions[start_address]['end_address']
                              + address_size, address_size):
                    if in_function_address in traces_addresses[
                                              traces_address_pointer:]:
                        function_covered = True
                        traces_address_pointer = traces_addresses.index(
                            in_function_address) + 1
                        break
                logger.info(f"Added non-sources function '{function_name}' "
                            f"with coverage: {function_covered}")
                if function_covered:
                    self.coverage.set_function_coverage((function_name,
                                                         function_source_file),
                                                        function_covered)


json_conf_help = """
Produces an intermediate json layer for code coverage reporting
using an input json configuration file.

Input json configuration file format:
{
    "configuration":
        {
        "remove_workspace": <true if 'workspace' must be from removed from the
                                path of the source files>,
        "include_assembly": <true to include assembly source code in the
                            intermediate layer>
        },
    "parameters":
        {
        "objdump": "<Path to the objdump binary to handle dwarf signatures>",
        "readelf: "<Path to the readelf binary to handle dwarf signatures>",
        "sources": [ <List of source code origins, one or more of the next
                        options>
                    {
                    "type": "git",
                    "URL":  "<URL git repo>",
                    "COMMIT": "<Commit id>",
                    "REFSPEC": "<Refspec>",
                    "LOCATION": "<Folder within 'workspace' where this source
                                is located>"
                    },
                    {
                    "type": "http",
                    "URL":  <URL link to file>",
                    "COMPRESSION": "xz",
                    "LOCATION": "<Folder within 'workspace' where this source
                                is located>"
                    }
                ],
        "workspace": "<Workspace folder where the source code was located to
                        produce the elf/axf files>",
        "output_file": "<Intermediate layer output file name and location>",
        "metadata": {<Metadata objects to be passed to the intermediate json
                    files>}
        },
    "elfs": [ <List of elf files to be traced/parsed>
            {
                    "name": "<Full path name to elf/axf file>",
                    "traces": [ <List of trace files to be parsed for this
                                elf/axf file>
                                "Full path name to the trace file,"
                              ]
                }
        ]
}
"""
OBJDUMP = None
READELF = None
FUNCTION_LINES_ENABLED = None


def main():
    global OBJDUMP
    global READELF
    global FUNCTION_LINES_ENABLED

    parser = argparse.ArgumentParser(epilog=json_conf_help,
                                     formatter_class=RawTextHelpFormatter)
    parser.add_argument('--config-json', metavar='PATH',
                        dest="config_json", default='config_file.json',
                        help='JSON configuration file', required=True)
    parser.add_argument('--local-workspace', default="",
                        help=('Local workspace folder where source code files'
                              ' and folders resides'))
    args = parser.parse_args()
    try:
        with open(args.config_json, 'r') as f:
            config = json.load(f)
    except Exception as ex:
        print("Error at opening and processing JSON: {}".format(ex))
        return
    print(json.dumps(config, indent=4))
    # Setting toolchain binary tools variables
    OBJDUMP = config['parameters']['objdump']
    READELF = config['parameters']['readelf']
    # Checking if are installed
    os_command("{} --version".format(OBJDUMP))
    os_command("{} --version".format(READELF))

    if args.local_workspace != "":
        # Checking ctags installed
        try:
            os_command("ctags --version")
        except BaseException:
            print("Warning!: ctags not installed/working function line numbers\
                    will be set to 0. [{}]".format(
                "sudo apt install exuberant-ctags"))
        else:
            FUNCTION_LINES_ENABLED = True

    intermediate_layer = IntermediateCodeCoverage(config, args.local_workspace)
    intermediate_layer.process()


if __name__ == '__main__':
    logger = cc_logger.logger
    start_time = time.time()
    main()
    elapsed_time = time.time() - start_time
    print("Elapsed time: {}s".format(elapsed_time))
