# Worst case analysis

from definitions import *
from pyopus.design.wc import WorstCase
# If MPI is imported an application not using MPI will behave correctly
# (i.e. only slot 0 will run the program) even when started with mpirun/mpiexec
from pyopus.parallel.mpi import MPI
from pyopus.parallel.cooperative import cOS
import sys

# Script arguments 
#   noop computes worst case without operating parameters (assumed initial)
#   nostat computes worst case without statistical parameters (assumed 0)
#   noopstat computes only the initial evaluation

if __name__=='__main__':
	atDesign={
		# Result of design across corners
		  'c_out':   3.4227551453164880e-13, 
         'diff_l':   7.4308192182875534e-07, 
         'diff_w':   1.2789110397149770e-06, 
         'load_l':   2.1097689639936013e-06, 
         'load_w':   2.3180449555941561e-06, 
         'mirr_l':   4.0529113121872304e-07, 
        'mirr_ld':   1.3311984218957902e-06, 
         'mirr_w':   3.4036562767439648e-05, 
        'mirr_wd':   2.3745920801687639e-06, 
        'mirr_wo':   2.1285465666785311e-05, 
          'out_l':   5.3631175887258056e-07, 
          'out_w':   2.6406246699146450e-05, 
          'r_out':   3.0372450962642072e+00, 
	}
	
	# Create corner with the Monte Carlo model, defined for all heads
	corners={
		'mc': {
			'params': {}, 
			'modules': [ 'mc' ]
		},
	}

	if len(sys.argv)>1 and sys.argv[1]=="noop":
		# No operating parameters
		# Add operating parameters to corner
		corners['mc']['params'].update({
			name: v['init'] for name, v in opParams.items()
		})
		opParams = {}
	elif len(sys.argv)>1 and sys.argv[1]=="nostat":
		# No statistical parameters
		corners['mc']['params'].update({
			name: 0.0 for name in statParams.keys()
		})
		statParams = {}
	elif len(sys.argv)>1 and sys.argv[1]=="noopstat":
		# No operating nor statistical parameters
		corners['mc']['params'].update({
			name: v['init'] for name, v in opParams.items()
		})
		opParams = {}
		corners['mc']['params'].update({
			name: 0.0 for name in statParams.keys()
		})
		statParams = {}
	
	# Worst case performances (skip area)
	wcList=list(measures.keys())
	wcList.sort()
	wcList.remove('area')

	# wcList = [ 'swing' ]
	
	# Prepare parallel environment
	cOS.setVM(MPI(mirrorMap={'*':'.'}, debug=0))
	
	# 3-sigma worst case
	wc=WorstCase(
		heads, analyses, measures, corners, statParams, opParams, variables=variables, 
		fixedParams=atDesign, 
		beta=3.0, sigmaBox=10, 
		stepTol=0.01, 
		debug=4, 
		screenOptions={'debug': 1}, 
		spawnerLevel=0
	)
	wcresults, analysisCount = wc(wcList)
	# wcresults, analysisCount = wc(['vgs_drv'])
	# wcresults, analysisCount = wc(['cmrr', 'vgs_drv'])
	# wcresults, analysisCount = wc(['cmrr'])
	
	print(wc.formatResults())
	print(wc.analysisCount)
	
	# Finalize cOS parallel environment
	cOS.finalize()

# Result	
# All parameters
#       cmrr >     5.78795e+01 o goal=   6.00000e+01 d=    2.99196e+00 neval= 426 2 OK
#       gain >     6.53782e+01   goal=   6.00000e+01 d=    3.00000e+00 neval= 114 1 OK
#       isup <     1.81109e-04   goal=   1.00000e-03 d=    3.00000e+00 neval= 115 1 OK
#     out_op >    -2.96816e-02 o goal=  -1.25000e-02 d=    3.00000e+00 neval= 115 1 OK
#     out_op <     3.70908e-02 o goal=   1.25000e-02 d=    3.00000e+00 neval= 117 1 OK
#   overshdn <     2.98573e-03   goal=   1.50000e-01 d=    3.00000e+00 neval= 131 1 OK
#   overshup <     8.97209e-03   goal=   1.50000e-01 d=    2.99145e+00 neval= 260 1 OK
#   ph_slope <    -0.00000e+00   goal=   0.00000e+00 d=    0.00000e+00 neval= 201 1 OK
#         pm >     6.35009e+01   goal=   5.00000e+01 d=    3.00000e+00 neval= 156 1 OK
#   psrr_vdd >     7.37693e+01   goal=   6.00000e+01 d=    2.99990e+00 neval= 421 3 OK
#   psrr_vss >     6.47977e+01   goal=   6.00000e+01 d=    2.99850e+00 neval= 440 2 OK
#     slewdn >     1.08529e+07   goal=   2.00000e+06 d=    3.00000e+00 neval= 126 1 OK
#     slewup >     1.08451e+07   goal=   2.00000e+06 d=    3.00000e+00 neval= 122 1 OK
#      swing >     1.30981e+00   goal=   1.00000e+00 d=    3.00000e+00 neval= 117 1 OK
#     tsetdn <     1.08013e-07   goal=   1.00000e-06 d=    3.00000e+00 neval= 121 1 OK
#     tsetup <     1.05258e-07   goal=   1.00000e-06 d=    3.00000e+00 neval= 122 1 OK
#       ugbw >     1.06617e+07   goal=   1.00000e+07 d=    3.00000e+00 neval= 127 1 OK
# vds_drv[0] >     4.17582e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 115 1 OK
# vds_drv[1] >     5.74703e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 115 1 OK
# vds_drv[2] >     3.04373e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 124 1 OK
# vds_drv[3] >     2.82845e-02   goal=   0.00000e+00 d=    3.00000e+00 neval= 111 1 OK
# vds_drv[4] >     7.10418e-01   goal=   0.00000e+00 d=    2.99614e+00 neval= 435 2 OK
# vds_drv[5] >     3.61454e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 130 1 OK
# vds_drv[6] >     2.14659e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 118 1 OK
# vds_drv[7] >     6.67981e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 299 2 OK
# vgs_drv[0] >     5.94209e-02   goal=   0.00000e+00 d=    3.00000e+00 neval= 114 1 OK
# vgs_drv[1] >     5.77977e-02   goal=   0.00000e+00 d=    3.00000e+00 neval= 114 1 OK
# vgs_drv[2] >     3.70164e-02   goal=   0.00000e+00 d=    3.00000e+00 neval= 120 1 OK
# vgs_drv[3] >     1.12405e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 131 1 OK
# vgs_drv[4] >     3.57837e-02   goal=   0.00000e+00 d=    3.00000e+00 neval= 111 1 OK
# vgs_drv[5] >     2.64637e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 114 1 OK
# vgs_drv[6] >     2.64872e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 112 1 OK
# vgs_drv[7] >     1.19771e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 180 2 OK
#
# No operating parameters
#       cmrr >     6.27849e+01   goal=   6.00000e+01 d=    3.00000e+00 neval= 153 2 OK
#       gain >     6.58352e+01   goal=   6.00000e+01 d=    3.00000e+00 neval=  92 1 OK
#       isup <     1.78746e-04   goal=   1.00000e-03 d=    3.00000e+00 neval=  89 1 OK
#     out_op >    -2.95161e-02 o goal=  -1.25000e-02 d=    3.00000e+00 neval=  89 1 OK
#     out_op <     3.63967e-02 o goal=   1.25000e-02 d=    3.00000e+00 neval=  90 1 OK
#   overshdn <     2.66214e-03   goal=   1.50000e-01 d=    2.99849e+00 neval= 196 2 OK
#   overshup <     8.32938e-03   goal=   1.50000e-01 d=    3.00000e+00 neval= 104 1 OK
#   ph_slope <    -0.00000e+00   goal=   0.00000e+00 d=    0.00000e+00 neval= 170 1 OK
#         pm >     6.35960e+01   goal=   5.00000e+01 d=    3.02386e+00 neval= 129 1 OK
#   psrr_vdd >     7.41518e+01   goal=   6.00000e+01 d=    3.00000e+00 neval= 198 2 OK
#   psrr_vss >     6.57440e+01   goal=   6.00000e+01 d=    2.98509e+00 neval= 172 2 OK
#     slewdn >     1.16922e+07   goal=   2.00000e+06 d=    3.00000e+00 neval=  95 1 OK
#     slewup >     1.16039e+07   goal=   2.00000e+06 d=    3.00000e+00 neval=  96 1 OK
#      swing >     1.45469e+00   goal=   1.00000e+00 d=    3.00000e+00 neval=  91 1 OK
#     tsetdn <     9.72761e-08   goal=   1.00000e-06 d=    3.00000e+00 neval=  95 1 OK
#     tsetup <     9.55943e-08   goal=   1.00000e-06 d=    3.00000e+00 neval=  96 1 OK
#       ugbw >     1.28872e+07   goal=   1.00000e+07 d=    3.00000e+00 neval=  91 1 OK
# vds_drv[0] >     5.28234e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  89 1 OK
# vds_drv[1] >     6.67601e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  89 1 OK
# vds_drv[2] >     3.95526e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  87 1 OK
# vds_drv[3] >     7.64192e-02   goal=   0.00000e+00 d=    3.00000e+00 neval=  89 1 OK
# vds_drv[4] >     7.79609e-01   goal=   0.00000e+00 d=    3.00000e+00 neval= 145 2 OK
# vds_drv[5] >     4.28147e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  87 1 OK
# vds_drv[6] >     2.97313e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  86 1 OK
# vds_drv[7] >     7.43442e-01   goal=   0.00000e+00 d=    2.99890e+00 neval= 303 4 OK
# vgs_drv[0] >     6.50929e-02   goal=   0.00000e+00 d=    3.00000e+00 neval=  93 1 OK
# vgs_drv[1] >     6.34355e-02   goal=   0.00000e+00 d=    3.00000e+00 neval=  93 1 OK
# vgs_drv[2] >     4.16202e-02   goal=   0.00000e+00 d=    3.00000e+00 neval=  87 1 OK
# vgs_drv[3] >     1.20440e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  90 1 OK
# vgs_drv[4] >     4.04903e-02   goal=   0.00000e+00 d=    3.00000e+00 neval=  90 1 OK
# vgs_drv[5] >     2.88266e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  90 1 OK
# vgs_drv[6] >     2.88266e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  90 1 OK
# vgs_drv[7] >     1.34516e-01   goal=   0.00000e+00 d=    3.00000e+00 neval=  88 1 OK
#
# No statistical parameters
#       cmrr >     6.60546e+01   goal=   6.00000e+01 d=              - neval=  23 1 OK
#       gain >     6.61221e+01   goal=   6.00000e+01 d=              - neval=  16 1 OK
#       isup <     1.74947e-04   goal=   1.00000e-03 d=              - neval=  17 1 OK
#     out_op >     3.28436e-03   goal=  -1.25000e-02 d=              - neval=  17 1 OK
#     out_op <     3.63388e-03   goal=   1.25000e-02 d=              - neval=  17 1 OK
#   overshdn <     1.00964e-03   goal=   1.50000e-01 d=              - neval=  18 1 OK
#   overshup <     4.09756e-03   goal=   1.50000e-01 d=              - neval=  29 1 OK
#   ph_slope <    -0.00000e+00   goal=   0.00000e+00 d=              - neval=  20 1 OK
#         pm >     6.59238e+01   goal=   5.00000e+01 d=              - neval=  24 1 OK
#   psrr_vdd >     9.23271e+01   goal=   6.00000e+01 d=              - neval=  17 1 OK
#   psrr_vss >     7.63926e+01   goal=   6.00000e+01 d=              - neval=  25 1 OK
#     slewdn >     1.18573e+07   goal=   2.00000e+06 d=              - neval=  17 1 OK
#     slewup >     1.17548e+07   goal=   2.00000e+06 d=              - neval=  17 1 OK
#      swing >     1.32949e+00   goal=   1.00000e+00 d=              - neval=  17 1 OK
#     tsetdn <     9.89417e-08   goal=   1.00000e-06 d=              - neval=  17 1 OK
#     tsetup <     9.69312e-08   goal=   1.00000e-06 d=              - neval=  17 1 OK
#       ugbw >     1.14927e+07   goal=   1.00000e+07 d=              - neval=  17 1 OK
# vds_drv[0] >     5.49319e-01   goal=   0.00000e+00 d=              - neval=  17 1 OK
# vds_drv[1] >     6.98113e-01   goal=   0.00000e+00 d=              - neval=  17 1 OK
# vds_drv[2] >     3.84865e-01   goal=   0.00000e+00 d=              - neval=  25 1 OK
# vds_drv[3] >     9.36227e-02   goal=   0.00000e+00 d=              - neval=  16 1 OK
# vds_drv[4] >     7.42680e-01   goal=   0.00000e+00 d=              - neval=  17 1 OK
# vds_drv[5] >     4.64263e-01   goal=   0.00000e+00 d=              - neval=  34 1 OK
# vds_drv[6] >     3.15203e-01   goal=   0.00000e+00 d=              - neval=  23 1 OK
# vds_drv[7] >     7.02975e-01   goal=   0.00000e+00 d=              - neval=  23 1 OK
# vgs_drv[0] >     6.75495e-02   goal=   0.00000e+00 d=              - neval=  16 1 OK
# vgs_drv[1] >     6.58998e-02   goal=   0.00000e+00 d=              - neval=  15 1 OK
# vgs_drv[2] >     4.39636e-02   goal=   0.00000e+00 d=              - neval=  24 1 OK
# vgs_drv[3] >     1.22089e-01   goal=   0.00000e+00 d=              - neval=  15 1 OK
# vgs_drv[4] >     4.41822e-02   goal=   0.00000e+00 d=              - neval=  15 1 OK
# vgs_drv[5] >     2.95236e-01   goal=   0.00000e+00 d=              - neval=  15 1 OK
# vgs_drv[6] >     2.95236e-01   goal=   0.00000e+00 d=              - neval=  16 1 OK
# vgs_drv[7] >     1.35309e-01   goal=   0.00000e+00 d=              - neval=  23 1 OK
#
# No operating nor statistical parameters
#       cmrr >     6.90735e+01   goal=   6.00000e+01 d=    0.00000e+00 neval=   1 0 OK
#       gain >     6.65743e+01   goal=   6.00000e+01 d=    0.00000e+00 neval=   1 0 OK
#       isup <     1.73096e-04   goal=   1.00000e-03 d=    0.00000e+00 neval=   1 0 OK
#     out_op >     3.43483e-03   goal=  -1.25000e-02 d=    0.00000e+00 neval=   1 0 OK
#     out_op <     3.43483e-03   goal=   1.25000e-02 d=    0.00000e+00 neval=   1 0 OK
#   overshdn <     8.16006e-04   goal=   1.50000e-01 d=    0.00000e+00 neval=   1 0 OK
#   overshup <     3.57388e-03   goal=   1.50000e-01 d=    0.00000e+00 neval=   1 0 OK
#   ph_slope <    -0.00000e+00   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
#         pm >     6.60650e+01   goal=   5.00000e+01 d=    0.00000e+00 neval=   1 0 OK
#   psrr_vdd >     9.47856e+01   goal=   6.00000e+01 d=    0.00000e+00 neval=   1 0 OK
#   psrr_vss >     8.00930e+01   goal=   6.00000e+01 d=    0.00000e+00 neval=   1 0 OK
#     slewdn >     1.28910e+07   goal=   2.00000e+06 d=    0.00000e+00 neval=   1 0 OK
#     slewup >     1.26872e+07   goal=   2.00000e+06 d=    0.00000e+00 neval=   1 0 OK
#      swing >     1.46976e+00   goal=   1.00000e+00 d=    0.00000e+00 neval=   1 0 OK
#     tsetdn <     8.83923e-08   goal=   1.00000e-06 d=    0.00000e+00 neval=   1 0 OK
#     tsetup <     8.74625e-08   goal=   1.00000e-06 d=    0.00000e+00 neval=   1 0 OK
#       ugbw >     1.39851e+07   goal=   1.00000e+07 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[0] >     6.56906e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[1] >     7.90213e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[2] >     4.75971e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[3] >     1.42808e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[4] >     8.12134e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[5] >     5.30362e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[6] >     3.98065e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vds_drv[7] >     7.78969e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[0] >     7.34953e-02   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[1] >     7.17793e-02   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[2] >     4.89422e-02   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[3] >     1.30400e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[4] >     4.92031e-02   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[5] >     3.20209e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[6] >     3.20209e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
# vgs_drv[7] >     1.50758e-01   goal=   0.00000e+00 d=    0.00000e+00 neval=   1 0 OK
