#!/usr/bin/env python3
#
#--------------------------------------------------------------------
# Parse the SPICE model files from sky130 and use the (commented out)
# statistics block to generate the correct monte carlo expressions
# in the device models for mismatch.
#--------------------------------------------------------------------

import os
import re
import sys

mm_switch_param = 'MC_MM_SWITCH'

options = []
arguments = []
for item in sys.argv[1:]:
    if item.find('-', 0) == 0:
        options.append(item[1:])
    else:
        arguments.append(item)

variant = 'sky130A'
walkpath = variant + '/libs.tech/ngspice'

if len(options) > 0:
    for option in options:
        if option.startswith('variant'):
            variant = option.split('=')[1]
    walkpath = variant + '/libs.ref/sky130_fd_pr/spice'
    for option in options: 
        if option == 'ef_format':
            walkpath = variant + '/libs.ref/spi/sky130_fd_pr'
elif len(arguments) > 0:
    walkpath = arguments[0]

mismatch_params = []

mmrex = re.compile('^\*[ \t]*mismatch[ \t]*\{')
endrex = re.compile('^\*[ \t]*\}')

filelist = []

#--------------------------------------------------------------------
# Step 1.  Gather variables
#--------------------------------------------------------------------

for dirpath, dirnames, filenames in os.walk(walkpath):
    for filename in filenames:
        if os.path.splitext(filename)[1] == '.spice':
            infile_name = os.path.join(dirpath, filename)
            filelist.append(infile_name)

            infile = open(infile_name, 'r')

            state = 'before_mismatch'
            line_number = 0
            replaced_something = False

            for line in infile:
                line_number += 1

                if state == 'before_mismatch':
                    mmatch = mmrex.match(line)
                    if mmatch:
                        state = 'in_mismatch'
                elif state == 'in_mismatch':
                    ematch = endrex.match(line)
                    if ematch:
                        state = 'after_mismatch'
                    else:
                        # Make sure all "A = B" syntax closes up around the equal sign.
                        newline = re.sub('[ \t]*=[ \t]*', '=', line)
                        tokens = newline.split()
                        if 'vary' in tokens:
                            if ('dist=gauss' in tokens) or ('gauss' in tokens):
                                gtype = 'A'
                                std_dev = 1
                                mismatch_param = tokens[2]
                                for token in tokens[3:]:
                                    gparam = token.split('=')
                                    if len(gparam) == 2:
                                        if gparam[0] == 'std':
                                            std_dev = float(gparam[1])
                                        elif gparam[0] == 'percent' and gparam[1] == 'yes':
                                            gtype = ''

                                if gtype == '':
                                    # Convert percentage to a fraction
                                    std_dev = std_dev / 100
                                repltext = '{}*' + gtype + 'GAUSS(0,{!s},1)'
                                replacement = repltext.format(mm_switch_param, std_dev)
                                mismatch_params.append((mismatch_param, replacement))
                            elif ('dist=lnorm' in tokens) or ('lnorm' in tokens):
                                mismatch_param = tokens[2]
                                std_dev = 1
                                for token in tokens[3:]:
                                    gparam = token.split('=')
                                    if len(gparam) == 2:
                                        if gparam[0] == 'std':
                                            std_dev = float(gparam[1])
                                replacement = '{}*EXP(AGAUSS(0,{!s},1))'.format(mm_switch_param, std_dev)
                                mismatch_params.append((mismatch_param, replacement))


            infile.close()

print('') 
print('Mismatch parameters found:')
for (mismatch_param, replacement) in mismatch_params:
     print(mismatch_param + ' : ' + replacement)
print('') 

#--------------------------------------------------------------------
# Create regexp for the alternative PSPICE "dev/gauss" syntax used in
# a number of places in the models.
#--------------------------------------------------------------------

gaussrex = re.compile('\'[ \t]+dev\/gauss=\'', re.IGNORECASE)

# Same as above, for parameters that are not already expressions.

gauss2rex = re.compile('=[ \t]*([^ \t]+)[ \t]+dev\/gauss=\'', re.IGNORECASE)

#--------------------------------------------------------------------
# Step 2.  Make replacements
#--------------------------------------------------------------------

for infile_name in filelist:

    filepath = os.path.split(infile_name)[0]
    filename = os.path.split(infile_name)[1]
    fileroot = os.path.splitext(filename)[0]
    outfile_name = os.path.join(filepath, fileroot + '_temp')

    infile = open(infile_name, 'r')
    outfile = open(outfile_name, 'w')

    state = 'before_mismatch'
    line_number = 0
    replaced_something = False

    for line in infile:
        line_number += 1
        newline = line

        gmatch = gaussrex.search(newline)
        if gmatch:
            newline = gaussrex.sub('+' + mm_switch_param + '*AGAUSS(0,1.0,1)*', newline)
            replaced_something = True
            print("  Line {}: Found PSPICE dev/gauss and replaced.".format(line_number))

        gmatch = gauss2rex.search(newline)
        if gmatch:
            newline = gauss2rex.sub("='\g<1>+" + mm_switch_param + '*AGAUSS(0,1.0,1)*', newline)
            replaced_something = True
            print("  Line {}: Found PSPICE dev/gauss and replaced.".format(line_number))

        if state == 'before_mismatch':
            outfile.write(newline)
            mmatch = mmrex.match(newline)
            if mmatch:
                state = 'in_mismatch'
        elif state == 'in_mismatch':
            outfile.write(newline)
            ematch = endrex.match(newline)
            if ematch:
                state = 'after_mismatch'
        elif state == 'after_mismatch':
            for (param, replacement) in mismatch_params:
                if param in newline:
                    newline = newline.replace(param, replacement)
                    replaced_something = True
                    print("  Line {}: Found mismatch parameter '{}' and replaced with '{}'.".format(line_number, param, replacement))
            outfile.write(newline)

    infile.close()
    outfile.close()
    if replaced_something:
        # print("Something was replaced in '{}', backed up original file"
        #	+ " and replaced with processed one.".format(infile_name))
        print("Something was replaced in '{}'.".format(infile_name))
        # os.rename(infile_name, infile_name + '.orig')
        os.rename(outfile_name, infile_name)
    else:
        print("Nothing was replaced in '{}'.".format(infile_name))
        os.remove(outfile_name)

