#!/bin/bash

export OCP=vtc_ocp
export NERO_H=vsc_halu3_nero
export NERO_V=vsc_valu3_nero
export PDV=pdv
export DRUC=druc
export COUGAR=cougar
export LVX=lvx
export S2R=s2r

export OCP_WIDEN=pnr_ocp_widen
export WIDE_FEEDTHS=pnr_wide_feedths
export BLOCK_INST=pnr_block_inst
export VIA_OVERLAP=pnr_via_do_overlap
export SIMPLE_BLOCK=pnr_simple_block

# adder4v is adder4 layout with vertical metal-2 or ALU2
# adder4h is adder4 layout with horizontal metal-2 or ALU2

export TECHNO_NAME_200=/usr/share/pharosc/etc/vsc200x.rds
export TECHNO_NAME_013=/usr/share/pharosc/etc/vsc013.rds
export TARGET_LIB=/usr/share/pharosc/alliance/cells/vsclib013
export SPI_MODEL=/usr/share/pharosc/etc/spimodel.cfg
export DREAL_TECHNO_200=/usr/share/pharosc/etc/s200.dreal
export GRAAL_TECHNO_200=/usr/share/pharosc/etc/s.graal
export DREAL_TECHNO_013=/usr/share/pharosc/etc/s013.dreal
export GRAAL_TECHNO_013=/usr/share/pharosc/etc/s.graal
export CATAL_NAME=VSCLIB013

export RDS_TECHNO_NAME=$TECHNO_NAME_200
export MBK_TARGET_LIB=$TARGET_LIB
export MBK_SPI_MODEL=$SPI_MODEL
export DREAL_TECHNO_NAME=$DREAL_TECHNO_200
export GRAAL_TECHNO_NAME=$GRAAL_TECHNO_200

export MBK_WORK_LIB=.
export MBK_IN_LO=vst
export MBK_OUT_LO=vst
export MBK_CATA_LIB=$MBK_TARGET_LIB
cp $MBK_TARGET_LIB/$CATAL_NAME LOCAL_CATAL
export MBK_CATAL_NAME=LOCAL_CATAL
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
$OCP -margin 0.10 -eqmargin -ioc ../ram4x4 -rows 8 ram4x4_6 ram4x4_p
$OCP_WIDEN ram4x4_p

$OCP -partial ram4x4_p -ioc ../ram4x4 ram4x4_6 ram4x4h_p
$OCP -partial ram4x4_p -ioc ../ram4x4 ram4x4_6 ram4x4v_p
$WIDE_FEEDTHS ram4x4h_p
$WIDE_FEEDTHS ram4x4v_p

# change ALU2 connectors to ALU3 for horizontal metal-2 (=metal-3 connectors N and S) and vice versa
sed -i 's/^C  *\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),NORTH,ALU2/C \1,\2,\3,\4,\5,NORTH,ALU3/' ram4x4h_p.ap
sed -i 's/^C  *\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),SOUTH,ALU2/C \1,\2,\3,\4,\5,SOUTH,ALU3/' ram4x4h_p.ap
sed -i 's/^C  *\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),EAST,ALU3/C \1,\2,\3,\4,\5,EAST,ALU2/' ram4x4h_p.ap
sed -i 's/^C  *\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),\([^,][^,]*\),WEST,ALU3/C \1,\2,\3,\4,\5,WEST,ALU2/' ram4x4h_p.ap
$BLOCK_INST ram4x4h_p H ram4x4h_bg
$BLOCK_INST ram4x4v_p V ram4x4v_bg

export NERO=$NERO_V
export MBK_WORK_LIB=.
export MBK_IN_LO=vst
export MBK_OUT_LO=vst
export MBK_CATA_LIB=$MBK_TARGET_LIB
export MBK_CATAL_NAME=LOCAL_CATAL
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
#
#                 FIRST HORIZONTAL ROUTE
#
nice -10 $NERO -v -H -2 -L -p ram4x4h_p ram4x4_6 ram4x4h
#    o  Allocating grid size [70,73,3].
# o  Routing stats :
#    - routing iterations    := 124637
#    - re-routing iterations := 29260
#    - ratio                 := 19.0127%.

sed -i '/zzzblock/ d' ram4x4h.ap
$PDV ram4x4h
#  - ALU2 length  :=      13504  (average length := 83)
#  - ALU3 length  :=       8560  (average length := 87)
#  - Total length :=      22064  (average length := 83)
#  - Total VIA    :=        426
#
#           Horizontal fix metal end overlap of VIA
#
$VIA_OVERLAP ram4x4h H

$SIMPLE_BLOCK ram4x4h TALU1 big
$SIMPLE_BLOCK ram4x4h TALU2 small
$SIMPLE_BLOCK ram4x4h TALU3 small
$SIMPLE_BLOCK ram4x4h TALU8 big

export NERO=$NERO_H
#
#                 FIRST VERTICAL ROUTE
#
nice -10 $NERO -v -H -2 -L -p ram4x4v_p ram4x4_6 ram4x4v
#    o  Allocating grid size [70,73,3].
# o  Routing stats :
#    - routing iterations    := 73804
#    - re-routing iterations := 5826
#    - ratio                 := 7.31634%.

sed -i '/zzzblock/ d' ram4x4v.ap
$PDV ram4x4v
#  - ALU2 length  :=       8552  (average length := 64)
#  - ALU3 length  :=      13104  (average length := 123)
#  - Total length :=      21656  (average length := 88)
#  - Total VIA    :=        430
#
#         VERTICAL fix metal end overlap of VIA
#
$VIA_OVERLAP ram4x4v V

$SIMPLE_BLOCK ram4x4v TALU1 big
$SIMPLE_BLOCK ram4x4v TALU2 small
$SIMPLE_BLOCK ram4x4v TALU3 small
$SIMPLE_BLOCK ram4x4v TALU8 big

export RDS_TECHNO_NAME=$TECHNO_NAME_200
export MBK_WORK_LIB=.
export RDS_IN=cif
export RDS_OUT=cif
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
export MBK_CATAL_NAME=LOCAL_CATAL
#
# HORIZONTAL DRC and use result to set blockages for reroute
#
$DRUC ram4x4h
# 100 errors

export NERO=$NERO_V
export RDS_TECHNO_NAME=$TECHNO_NAME_200
export MBK_WORK_LIB=.
export MBK_IN_LO=vst
export MBK_OUT_LO=vst
export MBK_CATA_LIB=$MBK_TARGET_LIB
export MBK_CATAL_NAME=LOCAL_CATAL
export RDS_IN=cif
export RDS_OUT=cif
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
#
#         HORIZONTAL Loop NERO until no DRC errors
#
./nero_loop ram4x4h H ram4x4_6
# Loop 1 with 100 errors and 0 blockages
# Loop 2 with 50 errors and 37 blockages
# Loop 3 with 46 errors and 54 blockages
# Loop 4 with 32 errors and 68 blockages
# Loop 5 with 14 errors and 78 blockages
# Loop 6 with 2 errors and 82 blockages
# Loop 7 with 0 errors and 83 blockages
$PDV ram4x4h
#  - ALU2 length  :=      14166  (average length := 26)
#  - ALU3 length  :=       9146  (average length := 28)
#  - Total length :=      23312  (average length := 26)
#  - Total VIA    :=        431

export RDS_TECHNO_NAME=$TECHNO_NAME_200
export MBK_WORK_LIB=.
export RDS_IN=cif
export RDS_OUT=cif
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
export MBK_CATAL_NAME=LOCAL_CATAL
#
# VERTICAL DRC and use result to set blockages for reroute
#
$DRUC ram4x4v
# 38 errors

export NERO=$NERO_H
export RDS_TECHNO_NAME=$TECHNO_NAME_200
export MBK_WORK_LIB=.
export MBK_IN_LO=vst
export MBK_OUT_LO=vst
export MBK_CATA_LIB=$MBK_TARGET_LIB
export MBK_CATAL_NAME=LOCAL_CATAL
export RDS_IN=cif
export RDS_OUT=cif
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
#
#         VERTICAL Loop NERO until no DRC errors
#
./nero_loop ram4x4v V ram4x4_6
# Loop 1 with 38 errors and 0 blockages
# Loop 2 with 12 errors and 16 blockages
# Loop 3 with 2 errors and 21 blockages
# Loop 4 with 6 errors and 22 blockages
# Loop 5 with 4 errors and 24 blockages
# Loop 6 with 6 errors and 26 blockages
# Loop 7 with 0 errors and 28 blockages
$PDV ram4x4v
#  - ALU2 length  :=       9242  (average length := 19)
#  - ALU3 length  :=      13536  (average length := 41)
#  - Total length :=      22778  (average length := 28)
#  - Total VIA    :=        428

export RDS_TECHNO_NAME=$TECHNO_NAME_200
export MBK_WORK_LIB=.
export MBK_IN_LO=vst
export MBK_OUT_LO=vst
export RDS_IN=cif
export RDS_OUT=cif
export MBK_CATA_LIB=$MBK_TARGET_LIB
cp $MBK_TARGET_LIB/$CATAL_NAME .
export MBK_CATAL_NAME=$CATAL_NAME
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
#
#                 Extract netlist from layout
#
$COUGAR -v -ac ram4x4h ram4x4h_lay
$COUGAR -v -ac ram4x4v ram4x4v_lay

export MBK_WORK_LIB=.
export MBK_IN_LO=vst
export MBK_OUT_LO=vst
export MBK_CATA_LIB=$MBK_TARGET_LIB
cp $MBK_TARGET_LIB/$CATAL_NAME .
export MBK_CATAL_NAME=$CATAL_NAME
#
#                           LVS
#
$LVX vst vst ram4x4_6 ram4x4h_lay -f | grep '^***** Netlists' | tee ram4x4h.lvs
$LVX vst vst ram4x4_6 ram4x4v_lay -f | grep '^***** Netlists' | tee ram4x4v.lvs

export RDS_TECHNO_NAME=$TECHNO_NAME_013
export MBK_WORK_LIB=.
export RDS_IN=cif
export RDS_OUT=cif
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
export MBK_CATA_LIB=$MBK_TARGET_LIB
cp $MBK_TARGET_LIB/$CATAL_NAME .
export MBK_CATAL_NAME=$CATAL_NAME
$DRUC ram4x4h
$DRUC ram4x4v

export RDS_TECHNO_NAME=$TECHNO_NAME_013
export DREAL_TECHNO_NAME=$DREAL_TECHNO_013
export GRAAL_TECHNO_NAME=$GRAAL_TECHNO_013
export MBK_WORK_LIB=.
export RDS_IN=cif
export RDS_OUT=cif
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
export MBK_CATA_LIB=.:$MBK_TARGET_LIB
cp $MBK_TARGET_LIB/$CATAL_NAME .
sed 's/ /usr/share/pharosc/' $CATAL_NAME > ${CATAL_NAME}_MERGE
export MBK_CATAL_NAME=${CATAL_NAME}_MERGE
#
#     Merge the CIF library cells to produce 0.13um layout
#
$S2R -v ram4x4h
$S2R -v ram4x4v

export RDS_TECHNO_NAME=$TECHNO_NAME_013
export DREAL_TECHNO_NAME=$DREAL_TECHNO_013
export GRAAL_TECHNO_NAME=$GRAAL_TECHNO_013
export MBK_WORK_LIB=.
export RDS_IN=gds
export RDS_OUT=gds
export MBK_IN_PH=ap
export MBK_OUT_PH=ap
export MBK_CATA_LIB=.:$MBK_TARGET_LIB
cp $MBK_TARGET_LIB/$CATAL_NAME .
sed 's/ /usr/share/pharosc/' $CATAL_NAME > ${CATAL_NAME}_MERGE
export MBK_CATAL_NAME=${CATAL_NAME}_MERGE
#
#                 Merge the GDS library cells
#
$S2R -v ram4x4h
$S2R -v ram4x4v

#
# Check and report the number of DRC and LVS errors
#
echo
for layout in ram4x4h ram4x4v
do
  drc_errors=$(grep -c 'ERROR Code' ${layout}.drc)
  if [ "$drc_errors" -eq 0 ]
  then
    echo "# No DRC errors in "$layout"."
  else
    echo "#! "$layout" has "$drc_errors" DRC errors. Please check."
  fi
  echo -n "# LVS result for "$layout" :"
  cat ${layout}.lvs
done

#export RDS_IN=cif
#export RDS_OUT=cif
#/usr/share/pharosc/bin/l2p -color -drawingsize=725x1068 -noheader -real -rflattentrans -nrfname -niname -nsname -scale=0.5 ram4x4
