#!/usr/bin/env python3
# Copyright 2020 The Skywater PDK Authors
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

import argparse
import json
import os
import re
import sys
from collections import defaultdict
from common import lib_extract_from_name, lib_extract_from_path
from pathlib import Path

debug = True
debug_print = lambda x: print(x) if debug else 0

sourcetodests = defaultdict(list)

Copyright_header = ('# Copyright 2020 The Skywater PDK Authors\n'
    '#\n'
    '# Licensed under the Apache License, Version 2.0 (the "License");\n'
    '# you may not use this file except in compliance with the License.\n'
    '# You may obtain a copy of the License at\n'
    '#\n'
    '#     https://www.apache.org/licenses/LICENSE-2.0\n'
    '#\n'
    '# Unless required by applicable law or agreed to in writing, software\n'
    '# distributed under the License is distributed on an "AS IS" BASIS,\n'
    '# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n'
    '# See the License for the specific language governing permissions and\n'
    '# limitations under the License.\n'
    '\n')

def create_file(module, header , main_cell_dir, lib_name):
    """
    >>> create_file('MACRO sky130_fd_io__smth END sky130_fd_io__smth', '', 'output/skywater-pdk/libraries/sky130_fd_io/V0.1.0/cells', 'sky130_fd_io')
    'output/skywater-pdk/libraries/sky130_fd_io/V0.1.0/cells/smth/sky130_fd_io__smth.lef'
    """
    global debug
    re_modname = re.compile(rf'{lib_name}\w*')
    full_name = re_modname.search(module)[0]
    module = module.replace(Copyright_header, '')
    header = header.replace(Copyright_header, '')
    module = Copyright_header + header + module + '[\n]END LIBRARY'
    mod_name = full_name.replace(lib_name + '__', '')
    # remove strenght spec from mod
    mod_name = re.sub(r'_[0-9][0-9]?$', '', mod_name)
    path = main_cell_dir + '/' + mod_name
    # write file
    file_path = path + '/' + full_name + '.lef'
    if debug:
        pass
    else:
        if not os.path.isdir(path):
            os.makedirs(path)
        with open(file_path, 'w') as f_out:
            f_out.write(module)
    return file_path


def main(input_file):
    global sourcetodests
    with open(input_file, 'r') as in_f:
        contents = in_f.read()
    main_cell_dir = "/".join(input_file.split("/")[:-1])+ "/cells"
    lib = lib_extract_from_path(input_file)

    header_end_index = contents.find('MACRO')
    header = contents[:header_end_index]
    cell_search  = re.findall(rf'(?s)MACRO {lib}\w*?[\n].*?END {lib}\w*', contents)
    if cell_search is not None:
        for cell in cell_search:
            out_f = create_file(cell, header, main_cell_dir, lib)
            print('\t' + out_f)
            sourcetodests[f].append(out_f)
    else:
        sys.exit(f"Cannot find a single module deifinition in file {input_file}.")
    #remove source file
    os.remove(input_file)


if __name__ == "__main__":
    import doctest
    fails, _ = doctest.testmod()
    if fails != 0:
        exit()
    else:
        print("Tests Passed")
    parser = argparse.ArgumentParser()
    parser.add_argument(
        "input",
        help="The path to the source directory",
        type=Path)
    parser.add_argument(
        "sourcetodests",
        help="Output file mapping input to output",
        type=Path)
    debug = False
    args = parser.parse_args()
    files = sorted(args.input.rglob('sky130_fd_sc_*.lef'))
    for f in files:
        f = str(f)
        print(f)
        main(f)
    with open(args.sourcetodests, 'w') as srctodest:
        json.dump(sourcetodests, srctodest, indent=2)



