Index: mpm-transport-01.00.05.02/Makefile
===================================================================
--- mpm-transport-01.00.05.02.orig/Makefile
+++ mpm-transport-01.00.05.02/Makefile
@@ -44,7 +44,7 @@
 CROSS_COMPILE ?= arm-linux-gnueabihf-
 ARFLAGS = crus
 LDFLAGS ?= -Wl,--hash-style=gnu
-CFLAGS ?= -march=armv7-a -marm -mthumb-interwork -mfloat-abi=hard -mfpu=neon -mtune=cortex-a15
+CFLAGS ?= -march=armv7-a -marm -mthumb-interwork -mfloat-abi=hard -mfpu=neon -mtune=cortex-a15 -O3
 EXTRA_CFLAGS = -g -ggdb2 -D_GNU_SOURCE -DARCH_$(ARCH) -Wall
 CC = $(CROSS_COMPILE)gcc $(SYSROOT_OPT) $(CFLAGS) $(EXTRA_CFLAGS)
 CC += -I$(STAGING_KERNEL_DIR)/include
Index: mpm-transport-01.00.05.02/src/transport/Makefile
===================================================================
--- mpm-transport-01.00.05.02.orig/src/transport/Makefile
+++ mpm-transport-01.00.05.02/src/transport/Makefile
@@ -80,7 +80,7 @@
 
 $(MPM_LIB)/$(MPMTRANSPORT_LIB_SO): $(MPMTRANSPORT_OBJS_SO)
 	@echo ***Archiving $@
-	$(CC) -Wl,-soname=$(MPMTRANSPORT_LIB_SO).1 $(PERIPHERAL_LIBS) -shared -fPIC -o $(MPMTRANSPORT_LIB_SO).1.0.0 $^
+	$(CC) $^ -Wl,-soname=$(MPMTRANSPORT_LIB_SO).1 $(PERIPHERAL_LIBS) -shared -fPIC -o $(MPMTRANSPORT_LIB_SO).1.0.0
 	@ln -s $(MPMTRANSPORT_LIB_SO).1.0.0 $(MPMTRANSPORT_LIB_SO).1
 	@ln -s $(MPMTRANSPORT_LIB_SO).1     $(MPMTRANSPORT_LIB_SO)
 	@mv -f $(MPMTRANSPORT_LIB_SO)* $(MPM_LIB)
Index: mpm-transport-01.00.05.02/src/transport/hyplnk/mpm_transport_hyplnk.c
===================================================================
--- mpm-transport-01.00.05.02.orig/src/transport/hyplnk/mpm_transport_hyplnk.c
+++ mpm-transport-01.00.05.02/src/transport/hyplnk/mpm_transport_hyplnk.c
@@ -44,6 +44,8 @@
 
 #define MAX_DEVICE_NAME_LEN 32
 
+extern void display_boost_att_termination(uint32_t index, uint32_t baseAddr, uint32_t numLanes, uint32_t check_point);
+extern void * internal_hyplnk_mmap(uint32_t addr, uint32_t size, int device_fd);
 /* Only one set of config can be active at one time. Keep track of it globally */
 hyplnk_peripheral hyplnkActiveIF[NUM_INTERFACES];
 
@@ -148,7 +150,6 @@
 
 	reg = mpm_transport_hyplnk_register_slave(sp);
 	if (reg < 0) return -1;
-
 	index = td->hyplnkIF;
 	if (hyplnkActiveIF[0].hyp_fd == 0) {
 		if (uioutil_check_device_exist("hyperlink0") == 1) {
@@ -213,6 +214,14 @@
 			}
 		}
 	}
+{
+uint32_t baseAddr1 = (uint32_t) internal_hyplnk_mmap(CSL_HYPERLINK_0_SERDES_CFG_REGS,0x2000, td->fd[0]);
+uint32_t baseAddr2 = (uint32_t) internal_hyplnk_mmap(CSL_HYPERLINK_1_SERDES_CFG_REGS,0x2000, td->fd[1]);
+display_boost_att_termination(0, baseAddr1, 4, 110);
+display_boost_att_termination(1, baseAddr2, 4, 210);
+munmap((void *)baseAddr1, 0x2000);
+munmap((void *)baseAddr2, 0x2000);
+}
 
 	return 0;
 
@@ -821,6 +830,7 @@
 		hyplnkActiveIF[1].hyp_fd = 0;
 	}
 	if (td) free(td);
+
 }
 
 uint32_t mpm_transport_hyplnk_phys_map64(mpm_transport_cfg_t *sp, uint64_t addr, uint32_t length, mpm_transport_mmap_t *mcfg)
@@ -1000,15 +1010,31 @@
 	if (hyplnkActiveIF[index].hyp_fd == -1) return -1;
 	td->fd[0] = hyplnkActiveIF[0].hyp_fd;
 	td->fd[1] = hyplnkActiveIF[1].hyp_fd;
-	
+
+	hyplnkInitCfg.dev.bases[0].cfgBase = internal_hyplnk_mmap((uint32_t)(hyplnkInitCfg.dev.bases[0].cfgBase), 0x100, td->fd[0]);
+    hyplnkInitCfg.dev.bases[1].cfgBase = internal_hyplnk_mmap((uint32_t)(hyplnkInitCfg.dev.bases[1].cfgBase), 0x100, td->fd[1]);
+	Hyplnk_init (&hyplnkInitCfg);
+
 	if ((reg==1) && (hyplnkActiveIF[((~index)&0x1)].slavesActive == 0))
 	{
 		hyplnkPSCSetup(0);
 		hyplnkPSCSetup(1);
+		usleep(10000);
+		//ret = hyplnkPeripheralSetup(td, 0, 5000, 1);
+		//ret &= hyplnkPeripheralSetup(td, 1, 5000, 1);
+		hyplnkPeripheralSetupTest(td, 0);
+		hyplnkPeripheralSetupTest(td, 1);
+		usleep(1000000);
 		if (hyplnkSerdesSetup(td, 0) == -1) {
 			mpm_printf(1, "Failed to setup serdes for hyperlink\n");
 			return -1;
 		}
+		usleep(1000000);
+		ret = hyplnkPeripheralSetup(td, 0, 5000, 1);
+		ret &= hyplnkPeripheralSetup(td, 1, 5000, 1);
+		usleep(1000000);
+		ret &= hyplnkPeripheralSetup(td, 0, 5000, 0);
+		ret &= hyplnkPeripheralSetup(td, 1, 5000, 0);
 	}
 
 	if (ret)
@@ -1031,6 +1057,8 @@
 	}
 	td->fd[0] = hyplnkActiveIF[0].hyp_fd;
 	td->fd[1] = hyplnkActiveIF[1].hyp_fd;
+	hyplnkInitCfg.dev.bases[0].cfgBase = (void *)CSL_HYPERLINK_0_SLV_CFG_REGS;
+	hyplnkInitCfg.dev.bases[1].cfgBase = (void *)CSL_HYPERLINK_1_SLV_CFG_REGS;
 	reg = mpm_transport_hyplnk_unregister_slave(sp);
 	if ((hyplnkActiveIF[0].slavesActive == 0) && (hyplnkActiveIF[1].slavesActive == 0)) {
 	    hyplnkSerdesDisable(td);
Index: mpm-transport-01.00.05.02/src/transport/hyplnk/mpm_transport_hyplnk_interface.c
===================================================================
--- mpm-transport-01.00.05.02.orig/src/transport/hyplnk/mpm_transport_hyplnk_interface.c
+++ mpm-transport-01.00.05.02/src/transport/hyplnk/mpm_transport_hyplnk_interface.c
@@ -34,6 +34,7 @@
 
 #include "mpm_transport_hyplnk_interface.h"
 #include "uioutils.h"
+#include "workaround.c"
 
 extern hyplnk_peripheral hyplnkActiveIF[NUM_INTERFACES];
 
@@ -82,7 +83,7 @@
 {
     CSL_SERDES_REF_CLOCK          refClock = CSL_SERDES_REF_CLOCK_312p5M;
     CSL_SERDES_LINK_RATE          linkRate = CSL_SERDES_LINK_RATE_6p25G;
-    uint32_t                      baseAddr;
+    uint32_t                      baseAddr, baseAddr1, baseAddr2;
     CSL_SERDES_RESULT             csl_retval;
     uint32_t                      i;
     CSL_SERDES_LANE_CTRL_RATE     lane_rate = CSL_SERDES_LANE_FULL_RATE;
@@ -93,7 +94,13 @@
     char lanerate[MAX_FILE_NAME_LEN];
     int conf_coeff = 1;
     csl_serdes_phy_type phy = SERDES_HYPERLINK;
+    uint32_t iTxTermNP;
+    int iAtt, iBoost;
+    FILE *fp;
+    fp = fopen("/var/log/mpmsrvdbg.log", "aw+");
     
+      baseAddr1 = (uint32_t) internal_hyplnk_mmap(CSL_HYPERLINK_0_SERDES_CFG_REGS,0x2000, hypCfg->fd[0]);
+      baseAddr2 = (uint32_t) internal_hyplnk_mmap(CSL_HYPERLINK_1_SERDES_CFG_REGS,0x2000, hypCfg->fd[1]);
     for (index=0; index<2; index++) {
       if (hypCfg->fd[index] == -1) continue;
       if (index == 0) {
@@ -164,6 +171,7 @@
 
       if (strcmp(lanerate,"full") == 0)
           lane_rate = CSL_SERDES_LANE_FULL_RATE;
+        //lane_rate = CSL_SERDES_LANE_HALF_RATE;
       else if (strcmp(lanerate,"half") == 0)
           lane_rate = CSL_SERDES_LANE_HALF_RATE;
       else if (strcmp(lanerate,"quarter") == 0)
@@ -178,32 +186,121 @@
       else 
         return -1;
 
-      baseAddr = (uint32_t) internal_hyplnk_mmap(serdes_regs,0x2000, hypCfg->fd[index]);
 
+	if (index==0) baseAddr = baseAddr1;
+	else baseAddr = baseAddr2;
+
+      // 1. load config file
       csl_retval = CSL_HyperlinkSerdesInit(baseAddr, refClock, linkRate);
       if (csl_retval != 0)
       {
           mpm_printf(1, "Invalid Serdes Init Params: %d\n", csl_retval);
       }
-      continue;
+
+      // 2. Enable PLL
+      /* SB PLL Enable */
+      CSL_HyperlinkSerdesPllEnable(baseAddr);
+ 
+
       for(i=0; i < hypCfg->hyplnkNumLanes; i++)
       {
+          // 3. Disable TX transmitter
+          disable_transmitter(baseAddr, i);
+
+          // 4. Enable Lanes
           CSL_HyperlinkSerdesLaneEnable(baseAddr, i, loopback, lane_rate);
-          if (conf_coeff) CSL_SERDES_CONFIG_CM_C1_C2(baseAddr, i, cm, c1, c2, phy);
       }
 
-      /* SB PLL Enable */
-      CSL_HyperlinkSerdesPllEnable(baseAddr);
+      // 5. Checks for PLL_LOCK and LANE_x_OK states
+      /* SB PLL Status Poll */
+        do
+        {
+            pllstat = CSL_HyperlinkSerdesGetStatus(baseAddr, hypCfg->hyplnkNumLanes);
+        }while(pllstat == CSL_SERDES_STATUS_PLL_NOT_LOCKED);
+
+        // 6. Get termination value
+        iTxTermNP = termination_workaround1(baseAddr, 1);
+#if 0
+}
+for (index=1; index>=0; index--) {
+	if (index==0) baseAddr = baseAddr1;
+	else baseAddr = baseAddr2;
+#endif
+
+    // 7. Assert Reset
+		fSerdesSbAssertReset(baseAddr);
+    // 8. Force LO signal [Optional]
+    //reset_cdr_att_boost(baseAddr, 4);
+
+      // 9. Set cm/c1/c2
+      for (i=0; i<4; i++) {
+        CSL_SERDES_CONFIG_CM_C1_C2(baseAddr, i, cm, c1, c2, phy);
+      }
+
+      // 10. Program the TX term values
+      termination_workaround2(baseAddr, 4, iTxTermNP);
+
+      // 11. Enable Transmitter
+      for (i=0; i<4; i++) enable_transmitter(baseAddr, i);
+
+      // 12. Deassert reset
+      fSerdesSbDeassertReset(baseAddr, 4);
+
+      // 13. Force signal detect [optional]
+      //deassert_reset_cdr_att_boost(baseAddr, 4);
 
       /* SB PLL Status Poll */
-      if (wait_for_lock) {
         do
         {
             pllstat = CSL_HyperlinkSerdesGetStatus(baseAddr, hypCfg->hyplnkNumLanes);
         }while(pllstat == CSL_SERDES_STATUS_PLL_NOT_LOCKED);
+      
+      // 14. Check rx valid
+      for (i=0; i<4; i++) {
+		    if (!check_rxvalid(baseAddr, i)) {
+          fprintf(fp, "rx valid check failed for lane %d, port %d\n", i, index);
+        }
+	     }
+#if 1
+        // 15. att/boost workaround
+        if (!boost_workaround(baseAddr, 4, 0)) {
+         fprintf(fp, "boost workaround failed for port %d\n"); 
+          return 1;
+        }
+#else
+    { /* Apply fixed attentuation and boost */
+      int jj;
+      iAtt   = 3;
+      iBoost = 3; //1..5
+      for (jj = 0; jj < 4; jj ++)
+      {
+	// 8)	Disable att/boost init cal and recal
+	// 9)	Set att and boost start values to the mean values found in step 7
+	fUserRegFillField32(baseAddr + 0xa00 + 0x84,9,1,0);  //Disable Rate2_cal_en [half rate] 
+	fUserRegFillField32(baseAddr + 0xa00 + 0x84,10,1,0); //Disable Rate3_cal_en [full rate]
+	//PhyB is at 9c for init cal
+	fUserRegFillField32(baseAddr + 0xa00 + 0x84,0,1,0);  //Disable Att init cal
+	fUserRegFillField32(baseAddr + 0xa00 + 0x8c,24,1,0); //Disable Att recal
+	fUserRegFillField32(baseAddr + (jj * 0x200) + 0x200 + 0x8c, 8,4,iAtt); //att start
+
+	fUserRegFillField32(baseAddr + 0xa00 + 0x84,1,1,0);  //Disable boost init cal
+	fUserRegFillField32(baseAddr + 0xa00 + 0x8c,25,1,0); //Disable boost recal
+  	fUserRegFillField32(baseAddr + (jj * 0x200) + 0x200 + 0x8c,12,4,iBoost); //boost start
       }
-      munmap((void *)baseAddr, 0x2000);
-   }
+      usleep(5000);
+    }
+#endif
+      fprintf(fp, "Initial hyplnkSerdesSetup: iTxTermNP is 0x%x\n", iTxTermNP);
+      for (i = 0; i < hypCfg->hyplnkNumLanes; i++) {
+        iAtt = iBoost = get_att_boost_values(baseAddr, i, 0);
+        iAtt = (iAtt >> 4) & 0x0f;
+        iBoost = (iBoost >> 8) & 0x0f;
+        fprintf(fp, "Initial hyplnkSerdesSetup: Hyperlink port %d, lane %d; Att = %d, Boost = %d\n", index, i, iAtt, iBoost);
+      }
+    }
+      munmap((void *)baseAddr1, 0x2000);
+      munmap((void *)baseAddr2, 0x2000);
+   fclose(fp);
    return 0;
 }
 
@@ -211,6 +308,9 @@
 {
     uint32_t baseAddr, i, serdes_regs = 0;
     int index;
+    int iAtt, iBoost;
+    FILE *fp;
+    fp = fopen("/var/log/mpmsrvdbg.log", "a+");
     for (index=0; index<2; index++) {
       if (hypCfg->fd[index] == -1) continue;
       if (index == 0)
@@ -218,6 +318,12 @@
       else if (index == 1)
           serdes_regs = CSL_HYPERLINK_1_SERDES_CFG_REGS;
       baseAddr = (uint32_t) internal_hyplnk_mmap(serdes_regs,0x2000, hypCfg->fd[index]);
+      for (i = 0; i < hypCfg->hyplnkNumLanes; i++) {
+        iAtt = iBoost = get_att_boost_values(baseAddr, i, 0);
+        iAtt = (iAtt >> 4) & 0x0f;
+        iBoost = (iBoost >> 8) & 0x0f;
+        fprintf(fp, "Exit hyplnkSerdesDisable: Hyperlink port %d, lane %d; Att = %d, Boost = %d\n", index, i, iAtt, iBoost);
+      }
       CSL_HyperlinkSerdesShutdown(baseAddr);
       CSL_SerDes_CMU_Restore_Default(baseAddr);
       CSL_SerDes_COMLANE_Restore_Default(baseAddr);
@@ -226,6 +332,104 @@
           CSL_SerDes_Lane_Restore_Default(baseAddr, i);
       }
     }
+    fclose(fp);
+}
+
+hyplnkRet_e hyplnkPeripheralSetupTest (mpm_transport_hyplnk_t *hypCfg, int index)
+{
+  hyplnkRevReg_t            rev;
+  hyplnkControlReg_t        control;
+  hyplnkStatusReg_t         status;
+  hyplnkLinkStatusReg_t     linkStatus;
+  hyplnkECCErrorsReg_t      ECCErrors;
+  hyplnkLanePwrMgmtReg_t    lanePwrMgmt;
+  hyplnkSERDESControl1Reg_t serdesControl1;
+  hyplnkTXAddrOvlyReg_t TXAddrOvly;
+
+  hyplnkRegisters_t setRegs;
+  hyplnkRegisters_t getRegs;
+
+  hyplnkRet_e retVal;
+  Hyplnk_Handle handle = NULL;
+  uint32_t i = 0, count = 0;
+  uint32_t baseAddr;
+
+  /* To prove the APIs work -- expose uninitialized variables */
+  memset (&rev,            0xff, sizeof(rev));
+  memset (&control,        0xff, sizeof(control));
+  memset (&status,         0xff, sizeof(status));
+  memset (&linkStatus,     0xff, sizeof(linkStatus));
+  memset (&ECCErrors,      0xff, sizeof(ECCErrors));
+  memset (&lanePwrMgmt,    0xff, sizeof(lanePwrMgmt));
+  memset (&serdesControl1, 0xff, sizeof(serdesControl1));
+  memset (&TXAddrOvly, 0, sizeof(TXAddrOvly));
+
+  /* Will always write these regs when writing */
+  memset (&setRegs, 0, sizeof(setRegs));
+  setRegs.control        = &control;
+  setRegs.status         = &status;
+  setRegs.ECCErrors      = &ECCErrors;
+  setRegs.lanePwrMgmt    = &lanePwrMgmt;
+  setRegs.serdesControl1 = &serdesControl1;
+  setRegs.TXAddrOvly     = &TXAddrOvly;
+
+  /* Will always read these regs when reading */
+  memset (&getRegs, 0, sizeof(getRegs));
+  getRegs.control        = &control;
+  getRegs.rev            = &rev;
+  getRegs.status         = &status;
+  getRegs.linkStatus     = &linkStatus;
+  getRegs.lanePwrMgmt    = &lanePwrMgmt;
+  getRegs.ECCErrors      = &ECCErrors;
+  getRegs.serdesControl1 = &serdesControl1;
+
+  if ((retVal = Hyplnk_open(index, &handle)) != hyplnk_RET_OK) {
+    mpm_printf(1, "Open failed\n");
+    return retVal;
+  }
+
+  /* Read rev and control */
+  if ((retVal = Hyplnk_readRegs (handle, hyplnk_LOCATION_LOCAL, &getRegs)) != hyplnk_RET_OK) {
+    mpm_printf(1, "Read revision register failed!\n");
+    return retVal;
+  }
+  status.lError       = 1; /* Clear any error */
+  status.rError       = 1; /* Clear any error */
+  ECCErrors.sglErrCor = 0;
+  ECCErrors.dblErrDet = 0;
+
+  lanePwrMgmt.singleLane = 0;
+  lanePwrMgmt.zeroLane   = 0;
+  lanePwrMgmt.quadLane   = 1;
+  serdesControl1.sleepCnt   = 0xff;
+  serdesControl1.disableCnt = 0xff;
+
+
+  /* Don't need to clear any more status bits */
+  setRegs.status         = NULL; 
+  setRegs.ECCErrors      = NULL;
+  //setRegs.lanePwrMgmt    = NULL;
+  //setRegs.serdesControl1 = NULL;
+
+  TXAddrOvly.txSecOvl    = 0;  
+  TXAddrOvly.txPrivIDOvl = hypCfg->hyplnkTxPrivID; 
+  TXAddrOvly.txIgnMask   = 10;
+  /* Take out of reset loopback */
+  control.reset           = 0;
+  control.statusIntEnable = 0;
+  control.intLocal        = 1;
+  control.iLoop           = (int) hypCfg->hyplnkDir;
+  if ((retVal = Hyplnk_writeRegs (handle, hyplnk_LOCATION_LOCAL, &setRegs)) != hyplnk_RET_OK) {
+    mpm_printf(1, "[2] Control register write failed!\n");
+    return retVal;
+  }
+
+
+  if ((retVal = Hyplnk_close (&handle)) != hyplnk_RET_OK) {
+    mpm_printf(1, "close failed!\n");
+    return retVal;
+  }
+  return hyplnk_RET_OK;
 }
 
 hyplnkRet_e hyplnkPeripheralSetup (mpm_transport_hyplnk_t *hypCfg, int index, uint32_t timeout, int reset)
@@ -244,7 +448,8 @@
 
   hyplnkRet_e retVal;
   Hyplnk_Handle handle = NULL;
-  uint32_t i = 0;
+  uint32_t i = 0, count = 0;
+  uint32_t baseAddr;
 
   /* To prove the APIs work -- expose uninitialized variables */
   memset (&rev,            0xff, sizeof(rev));
@@ -275,8 +480,13 @@
   getRegs.ECCErrors      = &ECCErrors;
   getRegs.serdesControl1 = &serdesControl1;
 
+  lanePwrMgmt.singleLane = 0;
+  lanePwrMgmt.zeroLane   = 0;
+  lanePwrMgmt.quadLane   = 1;
+  serdesControl1.sleepCnt   = 0xff;
+  serdesControl1.disableCnt = 0xff;
 
-  if ((retVal = Hyplnk_open((int)hypCfg->hyplnkIF, &handle)) != hyplnk_RET_OK) {
+  if ((retVal = Hyplnk_open(index, &handle)) != hyplnk_RET_OK) {
     mpm_printf(1, "Open failed\n");
     return retVal;
   }
@@ -295,11 +505,6 @@
     status.rError       = 1; /* Clear any error */
     ECCErrors.sglErrCor = 0;
     ECCErrors.dblErrDet = 0;
-    lanePwrMgmt.singleLane = 0;
-    lanePwrMgmt.zeroLane   = 0;
-    lanePwrMgmt.quadLane   = 1;
-    serdesControl1.sleepCnt   = 0xff;
-    serdesControl1.disableCnt = 0xff;
     if ((retVal = Hyplnk_writeRegs (handle, hyplnk_LOCATION_LOCAL, &setRegs)) != hyplnk_RET_OK) {
       mpm_printf(1, "[1] Control register write failed!\n");
       return retVal;
@@ -314,8 +519,8 @@
   /* Don't need to clear any more status bits */
   setRegs.status         = NULL; 
   setRegs.ECCErrors      = NULL;
-  setRegs.lanePwrMgmt    = NULL;
-  setRegs.serdesControl1 = NULL;
+  //setRegs.lanePwrMgmt    = NULL;
+  //setRegs.serdesControl1 = NULL;
 
   TXAddrOvly.txSecOvl    = 0;  
   TXAddrOvly.txPrivIDOvl = hypCfg->hyplnkTxPrivID; 
@@ -343,7 +548,17 @@
       usleep(1000);
       i++;
     }
-    if (i==timeout) break;
+    if (i==timeout) {
+      if (index == 0)
+        baseAddr = (uint32_t) internal_hyplnk_mmap(CSL_HYPERLINK_0_SERDES_CFG_REGS,0x2000, hypCfg->fd[0]);
+      else
+        baseAddr = (uint32_t) internal_hyplnk_mmap(CSL_HYPERLINK_1_SERDES_CFG_REGS,0x2000, hypCfg->fd[1]);
+      port_ok_workaround(baseAddr);
+      munmap((void *)baseAddr, 0x2000);
+      if (count == 5) break;
+      else i = 0;
+      count++;
+    }
   } while (1); 
 
   if ((retVal = Hyplnk_close (&handle)) != hyplnk_RET_OK) {
@@ -358,6 +573,49 @@
   return hyplnk_RET_OK;
 }
 
+void check_serdes_PLL(mpm_transport_hyplnk_t *hypCfg, int index) {
+  CSL_SERDES_STATUS pllstat;
+  uint32_t baseAddr, serdes_regs;
+  FILE *fp;
+  
+  fp = fopen("/var/log/mpmsrvdbg.log", "a+");
+  fprintf(fp, "check_serdes_PLL: checking...\n");
+  if (index == 0)
+      serdes_regs = CSL_HYPERLINK_0_SERDES_CFG_REGS;
+  else if (index == 1)
+      serdes_regs = CSL_HYPERLINK_1_SERDES_CFG_REGS;
+  baseAddr = (uint32_t) internal_hyplnk_mmap(serdes_regs,0x2000, hypCfg->fd[index]);
+  do
+  {
+    pllstat = CSL_HyperlinkSerdesGetStatus(baseAddr, hypCfg->hyplnkNumLanes);
+  } while(pllstat == CSL_SERDES_STATUS_PLL_NOT_LOCKED);
+  munmap((void *)baseAddr, 0x2000);
+  fprintf(fp, "check_serdes_PLL: got lock! CSL_HyperlinkSerdesGetStatus() returned ok\n");
+  fclose(fp);
+}
+void check_hyplnk_link(int index){
+  Hyplnk_Handle handle = NULL;
+  hyplnkRegisters_t getRegs;
+  hyplnkStatusReg_t status;
+  hyplnkRet_e retVal;
+  FILE *fp;
+  fp = fopen("/var/log/mpmsrvdbg.log", "a+");
+  fprintf(fp, "check_hyplnk_link: checking port %d...\n", index);
+
+  memset (&status, 0, sizeof(status));
+  memset (&getRegs, 0, sizeof(getRegs));
+  getRegs.status         = &status;
+  Hyplnk_open(index, &handle);
+  do {
+    if ((retVal = Hyplnk_readRegs (handle, hyplnk_LOCATION_LOCAL, &getRegs)) != hyplnk_RET_OK) {
+      mpm_printf(1, "Read status failed!\n");
+      return retVal;
+    }
+  } while( (!status.link) || (status.serialHalt) || (status.pllUnlock));
+  Hyplnk_close(&handle);
+  fprintf(fp, "check_hyplnk_link: got link!\n");
+  fclose(fp);
+}
 int mpm_transport_hyplnk_init_peripheral(mpm_transport_hyplnk_t *hypCfg, int index, uint32_t timeout)
 {
     hyplnkRet_e retVal;
@@ -375,25 +633,28 @@
     }
 
     hyplnkPSCSetup(index);
-    if ((retVal = hyplnkPeripheralSetup(hypCfg, index, timeout, 1)) != hyplnk_RET_OK)
-    {
-        mpm_printf(1, "Peripheral init reset failed, retVal = %d\n",retVal);
-        return -1;
-    }    
-    if ((hyplnkActiveIF[index].slavesActive == 1) && (hyplnkActiveIF[((~index)&0x1)].slavesActive == 0))
-    {
-      if (hypCfg->serdesInit) {
-        if (hyplnkSerdesSetup(hypCfg, 1) == -1) {
-          mpm_printf(1, "Failed to setup serdes for hyperlink 0\n");
+    if (hypCfg->serdesInit) {
+      if ((retVal = hyplnkPeripheralSetup(hypCfg, index, timeout, 1)) != hyplnk_RET_OK)
+      {
+          mpm_printf(1, "Peripheral init reset failed, retVal = %d\n",retVal);
+          return -1;
+      }    
+      if ((hyplnkActiveIF[index].slavesActive == 1) && (hyplnkActiveIF[((~index)&0x1)].slavesActive == 0))
+      {
+          if (hyplnkSerdesSetup(hypCfg, 1) == -1) {
+            mpm_printf(1, "Failed to setup serdes for hyperlink 0\n");
+            return -1;
+          }
+      }
+      if ((retVal = hyplnkPeripheralSetup(hypCfg, index, timeout, 0)) != hyplnk_RET_OK)
+      {
+          mpm_printf(1, "Peripheral setup failed, retVal = %d\n",retVal);
           return -1;
-        }
       }
     }
-    if ((retVal = hyplnkPeripheralSetup(hypCfg, index, timeout, 0)) != hyplnk_RET_OK)
-    {
-        mpm_printf(1, "Peripheral setup failed, retVal = %d\n",retVal);
-        return -1;
-    }
+
+    check_serdes_PLL(hypCfg, index);
+    check_hyplnk_link(index);
     return 0;
 }
 
@@ -447,7 +708,7 @@
     } while(setRegs.status->rPend);
 
     control.serialStop = 0;
-    control.reset = 1;
+    //control.reset = 1;
     if ((retVal = Hyplnk_writeRegs (handle, hyplnk_LOCATION_LOCAL, &setRegs)) != hyplnk_RET_OK) {
         mpm_printf(1, "Control register write failed!\n");
         return retVal;
Index: mpm-transport-01.00.05.02/src/transport/hyplnk/mpm_transport_hyplnk_interface.h
===================================================================
--- mpm-transport-01.00.05.02.orig/src/transport/hyplnk/mpm_transport_hyplnk_interface.h
+++ mpm-transport-01.00.05.02/src/transport/hyplnk/mpm_transport_hyplnk_interface.h
@@ -58,3 +58,6 @@
 void hyplnkPSCDisable(int port);
 int hyplnkSerdesSetup(mpm_transport_hyplnk_t *hypCfg, int wait_for_lock);
 void hyplnkSerdesDisable(mpm_transport_hyplnk_t *hypCfg);
+
+hyplnkRet_e hyplnkPeripheralSetup (mpm_transport_hyplnk_t *hypCfg, int index, uint32_t timeout, int reset);
+hyplnkRet_e hyplnkPeripheralSetupTest (mpm_transport_hyplnk_t *hypCfg, int index);
Index: mpm-transport-01.00.05.02/src/transport/hyplnk/workaround.c
===================================================================
--- /dev/null
+++ mpm-transport-01.00.05.02/src/transport/hyplnk/workaround.c
@@ -0,0 +1,287 @@
+void fSerdesSbCycleDelay(unsigned int n) {
+  int i;
+  for(i = 0; i<n; i++);
+}
+
+unsigned int fSerdesSbRead32(unsigned int addr)
+  {
+  return(*(volatile unsigned int *)(addr));
+  }
+
+unsigned int fSerdesSbReadTbusVal(unsigned int iSerdesCfgBase)
+{
+  	int iPhyA = (iSerdesCfgBase != 0x0231e000);
+  	unsigned int iTmp;
+
+  	if(iPhyA)
+   	 {
+   		iTmp  = (*(volatile unsigned int *)( iSerdesCfgBase + 0x0ec) >> 24) & 0x0ff;
+    	iTmp |= (*(volatile unsigned int *)( iSerdesCfgBase +  0x0fc) >> 16) & 0x00f00;
+   	 }
+   	else
+    {
+    	iTmp  = (*(volatile unsigned int *)( iSerdesCfgBase + 0x0f8) >> 16) & 0x0fff;
+    }
+  	return(iTmp);
+}
+
+void write_32_mask(unsigned int in_base,unsigned int iKeepMask,unsigned int iSetValue)
+{
+	unsigned int iTmp;
+
+  	iTmp = *(volatile unsigned int *)(in_base);
+	iTmp &= iKeepMask;
+ 	iTmp |= ((~iKeepMask)&iSetValue);
+  	*(volatile unsigned int *)( in_base) = iTmp; 
+}
+
+void fSerdesSbWriteTbusAddr(unsigned int iSerdesCfgBase, int iSelect, int iOffset)
+{
+    int iPhyA     = (iSerdesCfgBase != 0x0231e000);
+  int iTwoLaner;
+
+    iTwoLaner = (*(volatile unsigned int *)( iSerdesCfgBase + 0x1fc0)>>16)&0x0ffff;
+  if ((iTwoLaner==0x4eb9)||(iTwoLaner==0x4ebd)) iTwoLaner=0; else iTwoLaner=1;
+  if ((iSelect)&&(iTwoLaner)) iSelect++;
+
+   if (iPhyA)
+    {
+    write_32_mask(iSerdesCfgBase+0x0008, 0x00FFFFFF, (((iSelect) << 5) + iOffset) << 24);
+    }
+     else
+  {
+    write_32_mask(iSerdesCfgBase+0x00fc, 0xf800ffff, (((iSelect) << 8) + iOffset) << 16);
+  }
+}
+
+unsigned int fSerdesSbReadSelectedTbus(unsigned int iSerdesCfgBase,int iSelect,int iOffset)
+{
+  fSerdesSbWriteTbusAddr(iSerdesCfgBase,iSelect,iOffset);   //Set tbus address
+  return(fSerdesSbReadTbusVal(iSerdesCfgBase));             //Get TBUS Value
+}
+
+void fUserRegFillField32(uint32_t iAddress,uint32_t iOffset,uint32_t iWidth,uint32_t iValue)
+{
+  uint32_t iMask,iTmp;
+  uint32_t i;
+
+  for(i=0,iMask=0;i<iWidth;i++)
+  iMask = (iMask<<1)|1;
+  
+  iValue&=iMask;
+  iValue <<= iOffset;
+  iMask  <<= iOffset;
+  iTmp = *(volatile uint32_t *)(iAddress);
+  iTmp &= ~iMask;
+  iTmp |= iValue;
+  *(volatile uint32_t *)(iAddress) = iTmp;
+}
+
+int check_rxvalid(unsigned int in_base,int lane_no)
+  {
+
+    int timeoutloops=100000000;
+    unsigned int stat;
+    unsigned int iPhyB = (in_base == 0x0231e000);
+
+    //timeoutloops = TIMEOUTL;
+
+
+    // check for lnX_stat[3:2] to go high on both lanes, this indicates that adaptation has completed
+    // timeout for lanes that are not connected
+    stat= (fSerdesSbReadSelectedTbus(in_base,lane_no+1,0x2) & 0x0060) >> 5;
+    while ((stat != 3) && (timeoutloops != 0))
+    {
+                    stat= (fSerdesSbReadSelectedTbus(in_base,lane_no+1,0x2) & 0x0060) >> 5;
+                    timeoutloops--;
+    }
+
+
+//                              fSerdesSbCycleDelay(300000); // adding the rest of the delay ~ 300us
+    return timeoutloops;
+  }
+
+
+int boost_workaround(uint32_t in_base, int iLanes, int iPhyB) {
+  unsigned int boost_read=0, att_read=0,att_start;
+  int i;
+
+  for(i=0;i<iLanes;i++){
+
+        // first read initial att start value
+        att_start = (*(volatile unsigned int *)(in_base + (i * 0x200) + 0x200 + 0x8c)>>8)&0xF;
+
+        // check att value, fix this as start value turn off att adaptation and do boost readaptation
+        att_read = (fSerdesSbReadSelectedTbus(in_base,i+1,iPhyB?0x10:0x11)>>4)&0xF;
+        fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x8c,8,4,att_read); //att start
+        fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x9c,0,1,0);
+        fUserRegFillField32(in_base + 0x0a00 + 0x8c,24,1,0);
+
+        // force cal
+        fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x98,14,1,1);
+        fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x98,14,1,0);
+
+        if (!check_rxvalid(in_base,i)) return 0;
+
+        // check boost value
+        boost_read = (fSerdesSbReadSelectedTbus(in_base,i+1,iPhyB?0x10:0x11)>>8)&0xF;
+        // if boost=0, increment by 1
+        if (boost_read == 0) {
+
+            // set rxeq_ovr_en to 1
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,2,1,1);
+
+            // set rxeq_ovr_load_en for boost only
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,12,7,0x2);
+
+            // set rxeq_ovr_load for a value of 1
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,3,7,0x1);
+
+            // latch in new boost value
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,10,1,0x1);
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,10,1,0x0);
+
+            // reset previous registers
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,2,1,0x0);
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,12,7,0x0);
+            fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x2c,3,7,0x0);
+
+        }
+
+        //write back initial att start value
+        fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x8c,8,4,att_start); //att start
+        // turn back on att adaptation
+        fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x9c,0,1,1);
+        fUserRegFillField32(in_base + 0x0a00 + 0x8c,24,1,1);
+  }
+  return 1;
+}
+
+uint32_t termination_workaround1(uint32_t in_base, int iPhyA) {
+  return fSerdesSbReadSelectedTbus(in_base,0+1,(iPhyA)?(0x1b):(0x1a)) & 0x00ff;
+}
+
+void termination_workaround2(uint32_t in_base, int iLanes, uint32_t iTxTermNP) {
+  int i;
+  for(i=0;i<iLanes;i++)
+  {
+  fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x7c,24,8,iTxTermNP); //Set Tx Termination
+  fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x7c,20,1,1);    //Set termination override
+  }
+}
+
+uint32_t get_att_boost_values(uint32_t in_base, int lane_no, int iPhyB) {
+  return fSerdesSbReadSelectedTbus( in_base, lane_no+1, iPhyB?0x10:0x11);
+ }
+
+//rate 0 = full
+//rate 1 = half
+void rx_block_workaround(uint32_t in_base, int rate){
+  if (rate == 0)
+    fUserRegFillField32(in_base + 0x0a00 + 0x0c8, 0,6,0x03);
+  else if (rate == 1)
+    fUserRegFillField32(in_base + 0x0a00 + 0x0c4, 24,6,0x03);
+}
+
+// Force serdes signal detect LO
+void reset_cdr_att_boost(uint32_t in_base, int iLanes) {
+  int i;
+  for(i=0;i<iLanes;i++) fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x04,1,2,2);  
+}
+
+// Allow serdes to re-acquire Signal Detect
+void deassert_reset_cdr_att_boost(uint32_t in_base, int iLanes) {
+  int i;
+  for(i=0;i<iLanes;i++) fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x04,1,2,0);  
+}
+
+// Disable transmitter
+void disable_transmitter(uint32_t in_base, int iLane) {
+  fUserRegFillField32(in_base + (iLane * 0x200) + 0x200 + 0x0b8,16,2,3); //Disable transmitter
+}
+
+// Enable transmitter
+void enable_transmitter(uint32_t in_base, int iLane) {
+  fUserRegFillField32(in_base + (iLane * 0x200) + 0x200 + 0x0b8,16,2,0); //Enable Transmitter
+}
+
+void fSerdesSbAssertReset(unsigned int in_base)
+  {
+  int i;
+
+  //Assert reset while preserving the lnX_ctrl_i bits!
+
+  for(i=0;i<4;i++)
+    {
+    unsigned int uiTmp0,uiTmp1,uiTmpO;
+
+    uiTmp0=fSerdesSbReadSelectedTbus(in_base,i+1,0); //Read lnX_ctrl_i/lnX_pd_i
+    uiTmp1=fSerdesSbReadSelectedTbus(in_base,i+1,1); //Read lnX_rate_i
+    uiTmpO =  0;                          //Set Reset State
+    uiTmpO |= ((uiTmp1>>9)&0x003)<<1;     //Add user Rate
+    uiTmpO |= ((uiTmp0   )&0x003)<<3;     //Add user PD
+    uiTmpO |= ((uiTmp0>>2)&0x1FF)<<5;     //Add user ctrl_i
+    uiTmpO |= (1<<14);                    //Set Overide
+    uiTmpO &= ~0x60;                      //Try Clear the Tx Valid bits!
+
+    //Only modify the reset bit and the overlay bit
+
+    fUserRegFillField32(in_base + (i * 0x200) + 0x200 + 0x28,15,15,uiTmpO);
+    }
+  }
+
+void fSerdesSbDeassertReset(unsigned int in_base,int iLanes)
+  {
+  //Clear the Reset bit
+  fUserRegFillField32(in_base + (3 * 0x200) + 0x200 + 0x28,15,1,1);
+  fUserRegFillField32(in_base + (2 * 0x200) + 0x200 + 0x28,15,1,1);
+  fUserRegFillField32(in_base + (1 * 0x200) + 0x200 + 0x28,15,1,1);
+  fUserRegFillField32(in_base + (0 * 0x200) + 0x200 + 0x28,15,1,1);
+
+  //CHECK LANE OK for all lanes requested
+  if (iLanes)
+    {
+    unsigned int iTmp;
+    int i;
+
+    for(i=0,iTmp=0;i<iLanes;i++) iTmp=(iTmp<<1)|1;
+    iTmp=((fSerdesSbRead32(in_base + 0x1fc0 + 0x00)>>16)&1)?(iTmp<<28):(iTmp<<29);  //B8 or B4 OK Mask
+    while((fSerdesSbRead32(in_base + 0xa00 + 0x1f8) & iTmp) != iTmp);
+    }
+  //Clear Overlay bit
+  fUserRegFillField32(in_base + (3 * 0x200) + 0x200 + 0x28,29,1,0);
+  fUserRegFillField32(in_base + (2 * 0x200) + 0x200 + 0x28,29,1,0);
+  fUserRegFillField32(in_base + (1 * 0x200) + 0x200 + 0x28,29,1,0);
+  fUserRegFillField32(in_base + (0 * 0x200) + 0x200 + 0x28,29,1,0);
+  }
+
+void port_ok_workaround(uint32_t in_base)
+{
+  //
+  reset_cdr_att_boost(in_base, 4);
+
+  //
+  deassert_reset_cdr_att_boost(in_base, 4);
+
+  //
+  boost_workaround(in_base, 4, 0);
+}
+
+void display_boost_att_termination(uint32_t index, uint32_t baseAddr, uint32_t numLanes, uint32_t check_point)
+{
+uint32_t i, iAtt, iTxTermNP, iBoost;
+//FILE *fp = fopen ("/var/log/mpmsrv-disp.log", "a+");
+    iTxTermNP = termination_workaround1(baseAddr, 1);
+    //fprintf(fp, "%03d #port%d hyplnkSerdes: iTxTermNP is 0x%x\n", check_point, index, iTxTermNP);
+    printf("%03d #port%d hyplnkSerdes: iTxTermNP is 0x%x\n", check_point, index, iTxTermNP);
+    for (i = 0; i < numLanes; i++) {
+      iAtt = iBoost = get_att_boost_values(baseAddr, i, 0);
+      iAtt = (iAtt >> 4) & 0x0f;
+      iBoost = (iBoost >> 8) & 0x0f;
+      //fprintf(fp, "%03d #port%d hyplnkSerdes: lane %d; Att = %d, Boost = %d\n", check_point, index, i, iAtt, iBoost);
+      printf("%03d #port%d hyplnkSerdes: lane %d; Att = %d, Boost = %d\n", check_point, index, i, iAtt, iBoost);
+    }
+    fflush(stdout);
+//   fclose(fp);
+}
+/** nothing past this line ***/
Index: mpm-transport-01.00.05.02/src/transport/test/hyplnk/hyplnk_loopback/mpm_transport_hyplnk_loopback.c
===================================================================
--- mpm-transport-01.00.05.02.orig/src/transport/test/hyplnk/hyplnk_loopback/mpm_transport_hyplnk_loopback.c
+++ mpm-transport-01.00.05.02/src/transport/test/hyplnk/hyplnk_loopback/mpm_transport_hyplnk_loopback.c
@@ -94,7 +94,7 @@
 	mpm_transport_open_t ocfg = {
 		.open_mode	= (O_SYNC|O_RDWR),
 		.msec_timeout = 0,
-		.serdes_init = 1,
+		.serdes_init = 0,
 	};
 
 	mpm_transport_mmap_t mcfg = {
Index: mpm-transport-01.00.05.02/src/utils/uio/uioutils.c
===================================================================
--- mpm-transport-01.00.05.02.orig/src/utils/uio/uioutils.c
+++ mpm-transport-01.00.05.02/src/utils/uio/uioutils.c
@@ -65,10 +65,12 @@
 
 int uioutil_get_param_int(char *uio_name, char *param_name, int *buf)
 {
-	char filename[MAX_NAME_LENGTH];
+	char filename[MAX_LINE_LENGTH];
 	FILE *fp;
 	int ret = -1;
-	snprintf(filename, 35 + strlen(uio_name) + strlen(param_name), "/proc/device-tree/soc/%s/cfg-params/%s", uio_name, param_name);
+	int size = 35 + strlen(uio_name) + strlen(param_name);
+	if (size > MAX_LINE_LENGTH) return -1;
+	snprintf(filename, size, "/proc/device-tree/soc/%s/cfg-params/%s", uio_name, param_name);
 	fp = fopen(filename, "rb");
 	if (fp == NULL) return -1;
 	fread(&ret, sizeof(int), 1, fp);
@@ -83,7 +85,9 @@
 	char st[MAX_LINE_LENGTH];
 	FILE *fp;
 	char filename[MAX_LINE_LENGTH] = "";
-	snprintf(filename, 35 + strlen(uio_name) + strlen(param_name), "/proc/device-tree/soc/%s/cfg-params/%s", uio_name, param_name);
+	int size = 35 + strlen(uio_name) + strlen(param_name);
+	if (size > MAX_LINE_LENGTH) return -1;
+	snprintf(filename, size, "/proc/device-tree/soc/%s/cfg-params/%s", uio_name, param_name);
 	fp = fopen(filename, "r");
 	if (fp==NULL) return -1;
 	fscanf(fp, "%s", st);
