#!/usr/bin/env python3
# Copyright lowRISC contributors.
# Licensed under the Apache License, Version 2.0, see LICENSE for details.
# SPDX-License-Identifier: Apache-2.0
r"""Top Module Documentation Generator
"""
import os
from tabulate import tabulate

TABLE_HEADER = '''<!--
DO NOT EDIT THIS FILE DIRECTLY.
It has been generated with the following command:
'''


def set_md_table_font_size(row, size):
    """Wrap each row element with HTML tags and specify font size"""
    for k, elem in enumerate(row):
        row[k] = '<p style="font-size:' + str(size) + '">' + elem + '</p>'
    return row


def create_pinout_table(top, c_helper, target):
    """Create the pinout table for a specific target and extract some stats"""
    header = [
        "Pad Name", "Type", "Bank", "Connection", "Special Function",
        "Pinmux Insel Constant / Muxed Output Index", "Description"
    ]
    table_rows = [set_md_table_font_size(header, "smaller")]
    colalign = ("center", ) * len(header)

    # Pad stats
    stats = {}
    stats['muxed'] = 0
    stats['direct'] = 0
    stats['manual'] = 0

    # get all pads for this target
    pads = top['pinout']['pads'] + target['pinout']['add_pads']
    remove_pads = target['pinout']['remove_pads']
    special_signals = target['pinmux']['special_signals']

    # map pad names to special function signals
    special_pads = {}
    for sig in special_signals:
        special_pads.update({sig['pad']: {'name': sig['name'],
                                          'desc': sig['desc']}})

    i = 2  # insel enum starts at 2
    j = 0  # mio_out enum starts at 0
    for pad in pads:
        # get the corresponding insel constant and MIO output index
        if pad['connection'] == 'muxed':
            name, _, _ = c_helper.pinmux_insel.constants[i]
            insel = name.as_c_enum()
            name, _, _ = c_helper.pinmux_mio_out.constants[j]
            mio_out = name.as_c_enum()
            i += 1
            j += 1
        else:
            insel = "-"
            mio_out = "-"
        # check whether this pad needs to be dropped
        if pad['name'] in remove_pads:
            continue
        # gather some stats
        stats[pad['connection']] += 1
        # annotate special functions
        if pad['name'] in special_pads:
            special_func = special_pads[pad['name']]['name']
            desc = pad['desc'] + " / " + special_pads[pad['name']]['desc']
        else:
            special_func = "-"
            desc = pad['desc']
        row = [
            pad['name'],
            pad['type'],
            pad['bank'],
            pad['connection'],
            special_func,
            insel + ' / ' + mio_out,
            desc
        ]
        table_rows.append(set_md_table_font_size(row, "smaller"))

    ret_str = tabulate(table_rows,
                       headers="firstrow",
                       tablefmt="pipe",
                       colalign=colalign)

    return ret_str, stats


def create_pinmux_table(top, c_helper):
    """Create the pinmux connectivity table"""
    header = [
        "Module / Signal", "Connection", "Pad",
        "Pinmux Outsel Constant / Peripheral Input Index", "Description"
    ]
    table_rows = [set_md_table_font_size(header, "smaller")]
    colalign = ("center", ) * len(header)

    i = 3  # outsel enum starts at 3
    j = 0  # periph_input enum starts at 0
    for sig in top['pinmux']['ios']:
        port = sig['name']
        if sig['width'] > 1:
            port += '[' + str(sig['idx']) + ']'
        pad = sig['pad'] if sig['pad'] else '-'
        # get the corresponding insel constant
        if sig['connection'] == 'muxed' and sig['type'] in ['inout', 'output']:
            name, _, _ = c_helper.pinmux_outsel.constants[i]
            outsel = name.as_c_enum()
            i += 1
        else:
            outsel = "-"
        # get the corresponding peripheral input index
        if sig['connection'] == 'muxed' and sig['type'] in ['inout', 'input']:
            name, _, _ = c_helper.pinmux_peripheral_in.constants[j]
            periph_in = name.as_c_enum()
            j += 1
        else:
            periph_in = "-"
        row = [
            port,
            sig['connection'],
            pad,
            outsel + " / " + periph_in,
            sig['desc']
        ]
        table_rows.append(set_md_table_font_size(row, "smaller"))

    return tabulate(table_rows,
                    headers="firstrow",
                    tablefmt="pipe",
                    colalign=colalign)


def gen_pinmux_docs(top, c_helper, out_path):
    """Generate target summary table and linked subtables"""

    pinmux_path = out_path / '../ip/pinmux/doc'
    doc_path = out_path / 'ip/pinmux/doc/autogen'
    doc_path.mkdir(parents=True, exist_ok=True)

    # this is used to create relative hyperlinks from the summary table to
    # the individual target tables.
    relpath_prefix = os.path.relpath(doc_path.resolve(), pinmux_path.resolve())

    topname = top['name']
    gencmd = ("util/topgen.py -t hw/top_{topname}/data/top_{topname}.hjson "
              "-o hw/top_{topname}/\n\n".format(topname=topname))

    header = [
        "Target Name", "#IO Banks", "#Muxed Pads", "#Direct Pads",
        "#Manual Pads", "#Total Pads", "Pinout / Pinmux Tables"
    ]
    table_rows = [header]
    colalign = ("center", ) * len(header)

    for target in top['targets']:

        # create pinout/pinmux tables for this target
        pinout_table = '---\n'
        pinout_table += 'title: ' + target['name'].upper()
        pinout_table += ' Target Pinout and Pinmux Connectivity\n'
        pinout_table += '---\n'
        pinout_table += TABLE_HEADER + gencmd + "-->\n\n"
        pinout_table += '## Pinout Table\n\n'
        table_str, stats = create_pinout_table(top, c_helper, target)
        pinout_table += table_str + '\n'
        pinout_table += '## Pinmux Connectivity\n\n'
        pinout_table += create_pinmux_table(top, c_helper)

        pinout_table_path = doc_path / ("pinout_" + target['name'] + ".md")
        with open(pinout_table_path, 'w') as outfile:
            outfile.write(pinout_table)

        # gather some statistics
        num_banks = len(top['pinout']['banks'])
        # create summary table entry
        pinout_table_relpath = relpath_prefix + "/pinout_" + target['name'] + "/index.html"
        row = [
            target['name'].upper(),
            num_banks,
            stats['muxed'],
            stats['direct'],
            stats['manual'],
            stats['muxed'] + stats['direct'] + stats['manual'],
            "[Pinout Table](" + str(pinout_table_relpath) + ")"
        ]
        table_rows.append(row)

    summary_table = tabulate(table_rows,
                             headers="firstrow",
                             tablefmt="pipe",
                             colalign=colalign)
    summary_table = TABLE_HEADER + gencmd + "-->\n\n" + summary_table

    target_table_path = doc_path / "targets.md"
    with open(target_table_path, 'w') as target_outfile:
        target_outfile.write(summary_table)


def gen_top_docs(top, c_helper, out_path):
    # create pinout / pinmux specific tables for all targets
    gen_pinmux_docs(top, c_helper, out_path)
