vphy: hdmi: Updated to match IP fixes.
Signed-off-by: Andrei-Liviu Simion <andrei.simion@xilinx.com> Acked-by: Srikanth Vemula <svemula@xilinx.com>
This commit is contained in:
parent
5f495caaab
commit
c351438007
2 changed files with 258 additions and 136 deletions
|
@ -143,8 +143,6 @@ u32 XVphy_HdmiInitialize(XVphy *InstancePtr, u8 QuadId, XVphy_Config *CfgPtr,
|
|||
XVphy_HdmiSetSystemClockSelection(InstancePtr, QuadId);
|
||||
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTHE3) {
|
||||
XVphy_BufgGtReset(InstancePtr, XVPHY_DIR_TX,TRUE);
|
||||
XVphy_BufgGtReset(InstancePtr, XVPHY_DIR_RX,TRUE);
|
||||
XVphy_SetBufgGtDiv(InstancePtr, XVPHY_DIR_TX, 1);
|
||||
XVphy_SetBufgGtDiv(InstancePtr, XVPHY_DIR_RX, 1);
|
||||
}
|
||||
|
@ -152,12 +150,16 @@ u32 XVphy_HdmiInitialize(XVphy *InstancePtr, u8 QuadId, XVphy_Config *CfgPtr,
|
|||
XVPHY_DIR_RX, TRUE);
|
||||
XVphy_ResetGtPll(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
XVphy_ResetGtTxRx(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, TRUE);
|
||||
XVphy_ResetGtTxRx(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_ResetGtTxRx(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, TRUE);
|
||||
XVphy_ResetGtTxRx(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
}
|
||||
XVphy_PowerDownGtPll(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CMNA, TRUE);
|
||||
XVphy_PowerDownGtPll(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CHA, TRUE);
|
||||
XVphy_MmcmLockedMaskEnable(InstancePtr, QuadId, XVPHY_DIR_TX, TRUE);
|
||||
XVphy_MmcmLockedMaskEnable(InstancePtr, QuadId, XVPHY_DIR_RX, TRUE);
|
||||
XVphy_MmcmPowerDown(InstancePtr, QuadId, XVPHY_DIR_TX, TRUE);
|
||||
XVphy_MmcmPowerDown(InstancePtr, QuadId, XVPHY_DIR_RX, TRUE);
|
||||
XVphy_MmcmReset(InstancePtr, QuadId, XVPHY_DIR_TX, TRUE);
|
||||
|
@ -170,7 +172,14 @@ u32 XVphy_HdmiInitialize(XVphy *InstancePtr, u8 QuadId, XVphy_Config *CfgPtr,
|
|||
if (InstancePtr->Config.DruIsPresent) {
|
||||
XVphy_DruReset(InstancePtr, XVPHY_CHANNEL_ID_CHA, TRUE);
|
||||
XVphy_DruEnable(InstancePtr, XVPHY_CHANNEL_ID_CHA, FALSE);
|
||||
XVphy_DruSetGain(InstancePtr, XVPHY_CHANNEL_ID_CHA, 9, 16, 5);
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_DruSetGain(InstancePtr, XVPHY_CHANNEL_ID_CHA,
|
||||
9, 16, 5);
|
||||
}
|
||||
else {
|
||||
XVphy_DruSetGain(InstancePtr, XVPHY_CHANNEL_ID_CHA,
|
||||
9, 16, 4);
|
||||
}
|
||||
}
|
||||
|
||||
XVphy_SetRxLpm(InstancePtr, QuadId, XVPHY_CHANNEL_ID_CHA, XVPHY_DIR_RX,
|
||||
|
@ -185,8 +194,6 @@ u32 XVphy_HdmiInitialize(XVphy *InstancePtr, u8 QuadId, XVphy_Config *CfgPtr,
|
|||
/* Clear Interrupt Register */
|
||||
XVphy_WriteReg(InstancePtr->Config.BaseAddr, XVPHY_INTR_STS_REG,
|
||||
0xFFFFFFFF);
|
||||
XVphy_WriteReg(InstancePtr->Config.BaseAddr, XVPHY_INTR_STS_REG,
|
||||
0xFFFFFFFF);
|
||||
|
||||
/* Interrupt Enable. */
|
||||
XVphy_IntrEnable(InstancePtr, XVPHY_INTR_HANDLER_TYPE_TXRESET_DONE |
|
||||
|
@ -978,18 +985,24 @@ u32 XVphy_HdmiCfgCalcMmcmParam(XVphy *InstancePtr, u8 QuadId,
|
|||
|
||||
Div = 1;
|
||||
|
||||
if (((LineRate / 1000000) > 2970) && (Ppc == XVIDC_PPC_1)) {
|
||||
xil_printf("Error! The Video PHY cannot support this video ");
|
||||
xil_printf("format at PPC = 1\r\n");
|
||||
return (XST_FAILURE);
|
||||
}
|
||||
|
||||
/* In case of 4 pixels per clock, the M must be a multiple of four. */
|
||||
if (Ppc == XVIDC_PPC_4) {
|
||||
Mult = Mult / 4;
|
||||
Mult = Mult * 4;
|
||||
}
|
||||
/* Else the M must be a multiple of two. */
|
||||
else {
|
||||
else if (Ppc == XVIDC_PPC_2) {
|
||||
Mult = Mult / 2;
|
||||
Mult = Mult * 2;
|
||||
}
|
||||
|
||||
if (!((Mult > 1) && (Mult < 65))) {
|
||||
if (!((Mult >= 1) && (Mult < 65))) {
|
||||
return (XST_FAILURE); /* Mult is out of range. */
|
||||
}
|
||||
|
||||
|
@ -1014,53 +1027,85 @@ u32 XVphy_HdmiCfgCalcMmcmParam(XVphy *InstancePtr, u8 QuadId,
|
|||
/* Video clock. */
|
||||
switch (Bpc) {
|
||||
case XVIDC_BPC_10:
|
||||
/* Quad pixel. */
|
||||
if (Ppc == (XVIDC_PPC_4)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 5 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
else {
|
||||
/* Dual pixel. */
|
||||
else if (Ppc == (XVIDC_PPC_2)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 5 / 2 *
|
||||
((Dir == XVPHY_DIR_TX)?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
/* Single pixel. */
|
||||
else {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 5 / 4 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
break;
|
||||
case XVIDC_BPC_12:
|
||||
/* Quad pixel. */
|
||||
if (Ppc == (XVIDC_PPC_4)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 6 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
else {
|
||||
/* Dual pixel. */
|
||||
else if (Ppc == (XVIDC_PPC_2)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 3 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
/* Single pixel. */
|
||||
else {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 3 / 2 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
break;
|
||||
case XVIDC_BPC_16 :
|
||||
/* Quad pixel. */
|
||||
if (Ppc == (XVIDC_PPC_4)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 8 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
else {
|
||||
/* Dual pixel. */
|
||||
else if (Ppc == (XVIDC_PPC_2)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 4 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
/* Single pixel. */
|
||||
else {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 2 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
break;
|
||||
case XVIDC_BPC_8:
|
||||
default:
|
||||
/* Quad pixel. */
|
||||
if (Ppc == (XVIDC_PPC_4)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 4 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
else {
|
||||
/* Dual pixel. */
|
||||
else if (Ppc == (XVIDC_PPC_2)) {
|
||||
MmcmPtr->ClkOut2Div = (Mult * 2 *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
/* Single pixel. */
|
||||
else {
|
||||
MmcmPtr->ClkOut2Div = (Mult *
|
||||
((Dir == XVPHY_DIR_TX) ?
|
||||
(InstancePtr->HdmiTxSampleRate) : 1));
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -1097,19 +1142,31 @@ u32 XVphy_HdmiCfgCalcMmcmParam(XVphy *InstancePtr, u8 QuadId,
|
|||
(MmcmPtr->ClkOut2Div <= 128)) {
|
||||
Valid = (TRUE);
|
||||
}
|
||||
/* 4 pixels per clock. */
|
||||
else if (Ppc == (XVIDC_PPC_4)) {
|
||||
/* Decrease Mult value. */
|
||||
Mult -= 4;
|
||||
}
|
||||
/* 2 pixels per clock. */
|
||||
else {
|
||||
/* Decrease M value. */
|
||||
Mult -= 2;
|
||||
/* 4 pixels per clock. */
|
||||
if (Ppc == (XVIDC_PPC_4)) {
|
||||
/* Decrease Mult value. */
|
||||
Mult -= 4;
|
||||
}
|
||||
/* 2 pixels per clock. */
|
||||
else if (Ppc == (XVIDC_PPC_2)) {
|
||||
/* Decrease M value. */
|
||||
Mult -= 2;
|
||||
}
|
||||
/* 1 pixel per clock */
|
||||
else {
|
||||
/* Decrease M value */
|
||||
Mult -= 1;
|
||||
}
|
||||
}
|
||||
} while (!Valid);
|
||||
|
||||
return (XST_SUCCESS);
|
||||
if (Valid) {
|
||||
return (XST_SUCCESS);
|
||||
}
|
||||
else {
|
||||
return (XST_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
@ -1475,6 +1532,7 @@ u32 XVphy_HdmiCpllParam(XVphy *InstancePtr, u8 QuadId, XVphy_ChannelId ChId,
|
|||
"supported by this device\r\n");
|
||||
xil_printf(" "
|
||||
"Change to another format\r\n");
|
||||
return (XST_FAILURE);
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
@ -1557,7 +1615,8 @@ u32 XVphy_SetHdmiTxParam(XVphy *InstancePtr, u8 QuadId, XVphy_ChannelId ChId,
|
|||
|
||||
/* Verify arguments. */
|
||||
Xil_AssertNonvoid(InstancePtr != NULL);
|
||||
Xil_AssertNonvoid((Ppc == (XVIDC_PPC_2)) || (Ppc == (XVIDC_PPC_4)));
|
||||
Xil_AssertNonvoid((Ppc == (XVIDC_PPC_1)) || (Ppc == (XVIDC_PPC_2)) ||
|
||||
(Ppc == (XVIDC_PPC_4)));
|
||||
Xil_AssertNonvoid((Bpc == (XVIDC_BPC_8)) || (Bpc == (XVIDC_BPC_10)) ||
|
||||
(Bpc == (XVIDC_BPC_12)) || (Bpc == (XVIDC_BPC_16)));
|
||||
Xil_AssertNonvoid((ColorFormat == (XVIDC_CSF_RGB)) ||
|
||||
|
@ -1579,6 +1638,10 @@ u32 XVphy_SetHdmiTxParam(XVphy *InstancePtr, u8 QuadId, XVphy_ChannelId ChId,
|
|||
XVphy_WriteCfgRefClkSelReg(InstancePtr, QuadId);
|
||||
|
||||
}
|
||||
|
||||
if (Status == XST_FAILURE) {
|
||||
return Status;
|
||||
}
|
||||
}
|
||||
/* Bonded mode. */
|
||||
else {
|
||||
|
@ -1601,6 +1664,15 @@ u32 XVphy_SetHdmiTxParam(XVphy *InstancePtr, u8 QuadId, XVphy_ChannelId ChId,
|
|||
Status = (XST_SUCCESS);
|
||||
}
|
||||
|
||||
/* Is HDMITXSS PPC match with VPHY PPC? */
|
||||
if (Ppc == InstancePtr->Config.Ppc) {
|
||||
Status = (XST_SUCCESS);
|
||||
}
|
||||
else {
|
||||
xil_printf("Warning: HDMI TX SS PPC = %d, doesn't match with"
|
||||
" VPhy PPC = %d\r\n",Ppc, InstancePtr->Config.Ppc);
|
||||
Status = (XST_FAILURE);
|
||||
}
|
||||
if (Status == (XST_SUCCESS)) {
|
||||
/* Calculate TXPLL parameters.
|
||||
* In HDMI the colordepth in YUV422 is always 12 bits,
|
||||
|
@ -1616,8 +1688,6 @@ u32 XVphy_SetHdmiTxParam(XVphy *InstancePtr, u8 QuadId, XVphy_ChannelId ChId,
|
|||
Status = XVphy_HdmiCfgCalcMmcmParam(InstancePtr, QuadId,
|
||||
ChId, XVPHY_DIR_TX, Ppc, Bpc);
|
||||
}
|
||||
|
||||
Status = (XST_SUCCESS);
|
||||
}
|
||||
else {
|
||||
Status = (XST_FAILURE);
|
||||
|
|
|
@ -198,8 +198,7 @@ void XVphy_HdmiQpllLockHandler(XVphy *InstancePtr)
|
|||
XVphy_PllType TxPllType;
|
||||
XVphy_PllType RxPllType;
|
||||
u8 Id, Id0, Id1;
|
||||
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_QPLL_LOCK, 1);
|
||||
XVphy_ChannelId ChId;
|
||||
|
||||
TxStatePtr = &InstancePtr->Quads[0].Plls[0].TxState;
|
||||
RxStatePtr = &InstancePtr->Quads[0].Plls[0].RxState;
|
||||
|
@ -210,57 +209,97 @@ void XVphy_HdmiQpllLockHandler(XVphy *InstancePtr)
|
|||
RxPllType = XVphy_GetPllType(InstancePtr, 0, XVPHY_DIR_RX,
|
||||
XVPHY_CHANNEL_ID_CH1);
|
||||
|
||||
/* Check if we are really waiting for a QPLL lock. */
|
||||
if (!((((RxPllType == XVPHY_PLL_TYPE_QPLL) ||
|
||||
(RxPllType == XVPHY_PLL_TYPE_QPLL0) ||
|
||||
(RxPllType == XVPHY_PLL_TYPE_QPLL1)) &&
|
||||
(*RxStatePtr == XVPHY_GT_STATE_LOCK)) ||
|
||||
(((TxPllType == XVPHY_PLL_TYPE_QPLL) ||
|
||||
(TxPllType == XVPHY_PLL_TYPE_QPLL0) ||
|
||||
(TxPllType == XVPHY_PLL_TYPE_QPLL1)) &&
|
||||
(*TxStatePtr == XVPHY_GT_STATE_LOCK)))) {
|
||||
return;
|
||||
}
|
||||
|
||||
/* RX is using QPLL. */
|
||||
if ((RxPllType == XVPHY_PLL_TYPE_QPLL) ||
|
||||
(RxPllType == XVPHY_PLL_TYPE_QPLL0) ||
|
||||
(RxPllType == XVPHY_PLL_TYPE_QPLL1)) {
|
||||
/* GT RX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, FALSE);
|
||||
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA, &Id0, &Id1);
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].RxState =
|
||||
XVPHY_GT_STATE_RESET;
|
||||
/* Determine which channel(s) to operate on. */
|
||||
switch (RxPllType) {
|
||||
case XVPHY_PLL_TYPE_QPLL:
|
||||
case XVPHY_PLL_TYPE_QPLL0:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN0;
|
||||
break;
|
||||
case XVPHY_PLL_TYPE_QPLL1:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN1;
|
||||
break;
|
||||
default:
|
||||
ChId = XVPHY_CHANNEL_ID_CHA;
|
||||
break;
|
||||
}
|
||||
|
||||
/* If the GT TX and RX are coupled, then update the GT TX state
|
||||
* as well. */
|
||||
if (XVphy_IsBonded(InstancePtr, 0, XVPHY_CHANNEL_ID_CH1)) {
|
||||
if (XVphy_IsPllLocked(InstancePtr, 0, ChId) == XST_SUCCESS) {
|
||||
/* Log, lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_QPLL_LOCK, 1);
|
||||
|
||||
/* GT RX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, FALSE);
|
||||
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA, &Id0,
|
||||
&Id1);
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].
|
||||
RxState = XVPHY_GT_STATE_RESET;
|
||||
}
|
||||
|
||||
/* If the GT TX and RX are coupled, then update the GT
|
||||
* TX state as well. */
|
||||
if (XVphy_IsBonded(InstancePtr, 0,
|
||||
XVPHY_CHANNEL_ID_CH1)) {
|
||||
/* GT TX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0,
|
||||
XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA,
|
||||
&Id0, &Id1);
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[
|
||||
XVPHY_CH2IDX(Id)].
|
||||
TxState = XVPHY_GT_STATE_RESET;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* Log, Lost lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_QPLL_LOCK, 0);
|
||||
}
|
||||
}
|
||||
/* TX is using QPLL. */
|
||||
else {
|
||||
/* Determine which channel(s) to operate on. */
|
||||
switch (TxPllType) {
|
||||
case XVPHY_PLL_TYPE_QPLL:
|
||||
case XVPHY_PLL_TYPE_QPLL0:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN0;
|
||||
break;
|
||||
case XVPHY_PLL_TYPE_QPLL1:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN1;
|
||||
break;
|
||||
default:
|
||||
ChId = XVPHY_CHANNEL_ID_CHA;
|
||||
break;
|
||||
}
|
||||
|
||||
if (XVphy_IsPllLocked(InstancePtr, 0, ChId) == XST_SUCCESS) {
|
||||
/* Log, lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_QPLL_LOCK, 1);
|
||||
|
||||
/* GT TX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
XVPHY_DIR_TX, FALSE);
|
||||
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA,
|
||||
&Id0, &Id1);
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA, &Id0,
|
||||
&Id1);
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].
|
||||
TxState = XVPHY_GT_STATE_RESET;
|
||||
}
|
||||
}
|
||||
}
|
||||
/* TX is using QPLL. */
|
||||
else {
|
||||
/* GT TX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, FALSE);
|
||||
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA, &Id0, &Id1);
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].TxState =
|
||||
XVPHY_GT_STATE_RESET;
|
||||
else {
|
||||
/* Log, Lost lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_QPLL_LOCK, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -283,8 +322,7 @@ void XVphy_HdmiCpllLockHandler(XVphy *InstancePtr)
|
|||
XVphy_PllType TxPllType;
|
||||
XVphy_PllType RxPllType;
|
||||
u8 Id, Id0, Id1;
|
||||
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_CPLL_LOCK, 1);
|
||||
XVphy_ChannelId ChId;
|
||||
|
||||
TxStatePtr = &InstancePtr->Quads[0].Plls[0].TxState;
|
||||
RxStatePtr = &InstancePtr->Quads[0].Plls[0].RxState;
|
||||
|
@ -295,49 +333,90 @@ void XVphy_HdmiCpllLockHandler(XVphy *InstancePtr)
|
|||
RxPllType = XVphy_GetPllType(InstancePtr, 0, XVPHY_DIR_RX,
|
||||
XVPHY_CHANNEL_ID_CH1);
|
||||
|
||||
/* Check if we are really waiting for a CPLL lock. */
|
||||
if (!(((RxPllType == XVPHY_PLL_TYPE_CPLL) &&
|
||||
(*RxStatePtr == XVPHY_GT_STATE_LOCK)) ||
|
||||
((TxPllType == XVPHY_PLL_TYPE_CPLL) &&
|
||||
(*TxStatePtr == XVPHY_GT_STATE_LOCK)))) {
|
||||
return;
|
||||
}
|
||||
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA, &Id0, &Id1);
|
||||
|
||||
/* RX is using CPLL. */
|
||||
if (RxPllType == XVPHY_PLL_TYPE_CPLL) {
|
||||
/* GT RX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, FALSE);
|
||||
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].RxState =
|
||||
XVPHY_GT_STATE_RESET;
|
||||
/* Determine which channel(s) to operate on. */
|
||||
switch (RxPllType) {
|
||||
case XVPHY_PLL_TYPE_QPLL:
|
||||
case XVPHY_PLL_TYPE_QPLL0:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN0;
|
||||
break;
|
||||
case XVPHY_PLL_TYPE_QPLL1:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN1;
|
||||
break;
|
||||
default:
|
||||
ChId = XVPHY_CHANNEL_ID_CHA;
|
||||
break;
|
||||
}
|
||||
|
||||
/* If the GT TX and RX are coupled, then update the GT TX state
|
||||
* as well. */
|
||||
if (XVphy_IsBonded(InstancePtr, 0, XVPHY_CHANNEL_ID_CH1)) {
|
||||
if (XVphy_IsPllLocked(InstancePtr, 0, ChId) == XST_SUCCESS) {
|
||||
/* Log, lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_CPLL_LOCK, 1);
|
||||
|
||||
/* GT RX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, FALSE);
|
||||
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].
|
||||
RxState = XVPHY_GT_STATE_RESET;
|
||||
}
|
||||
|
||||
/* If the GT TX and RX are coupled, then update the GT
|
||||
* TX state as well. */
|
||||
if (XVphy_IsBonded(InstancePtr, 0,
|
||||
XVPHY_CHANNEL_ID_CH1)) {
|
||||
/* GT TX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0,
|
||||
XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[
|
||||
XVPHY_CH2IDX(Id)].
|
||||
TxState = XVPHY_GT_STATE_RESET;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* Log, Lost lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_CPLL_LOCK, 0);
|
||||
}
|
||||
}
|
||||
/* TX is using CPLL. */
|
||||
else {
|
||||
/* Determine which channel(s) to operate on. */
|
||||
switch (TxPllType) {
|
||||
case XVPHY_PLL_TYPE_QPLL:
|
||||
case XVPHY_PLL_TYPE_QPLL0:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN0;
|
||||
break;
|
||||
case XVPHY_PLL_TYPE_QPLL1:
|
||||
ChId = XVPHY_CHANNEL_ID_CMN1;
|
||||
break;
|
||||
default:
|
||||
ChId = XVPHY_CHANNEL_ID_CHA;
|
||||
break;
|
||||
}
|
||||
|
||||
if (XVphy_IsPllLocked(InstancePtr, 0, ChId) == XST_SUCCESS) {
|
||||
/* Log, lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_CPLL_LOCK, 1);
|
||||
|
||||
/* GT TX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
XVPHY_DIR_TX, FALSE);
|
||||
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].
|
||||
TxState = XVPHY_GT_STATE_RESET;
|
||||
}
|
||||
}
|
||||
}
|
||||
/* TX is using CPLL. */
|
||||
else {
|
||||
/* GT TX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, FALSE);
|
||||
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
InstancePtr->Quads[0].Plls[XVPHY_CH2IDX(Id)].TxState =
|
||||
XVPHY_GT_STATE_RESET;
|
||||
else {
|
||||
/* Log, Lost lock */
|
||||
XVphy_LogWrite(InstancePtr, XVPHY_LOG_EVT_CPLL_LOCK, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -483,9 +562,6 @@ void XVphy_HdmiTxClkDetFreqChangeHandler(XVphy *InstancePtr)
|
|||
/* If the TX frequency has changed, the PLL is always disabled. */
|
||||
XVphy_PowerDownGtPll(InstancePtr, 0, (PllType == XVPHY_PLL_TYPE_CPLL) ?
|
||||
XVPHY_CHANNEL_ID_CHA : XVPHY_CHANNEL_ID_CMNA, TRUE);
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTHE3) {
|
||||
XVphy_BufgGtReset(InstancePtr, XVPHY_DIR_TX,TRUE);
|
||||
}
|
||||
XVphy_ResetGtPll(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA, XVPHY_DIR_TX,
|
||||
TRUE);
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
|
@ -504,8 +580,10 @@ void XVphy_HdmiTxClkDetFreqChangeHandler(XVphy *InstancePtr)
|
|||
XVphy_TxAlignStart(InstancePtr, XVPHY_CHANNEL_ID_CHA, FALSE);
|
||||
|
||||
/* De-assert GT TX reset. */
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, FALSE);
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, FALSE);
|
||||
}
|
||||
|
||||
XVphy_Ch2Ids(InstancePtr, XVPHY_CHANNEL_ID_CHA, &Id0, &Id1);
|
||||
for (Id = Id0; Id <= Id1; Id++) {
|
||||
|
@ -550,11 +628,6 @@ void XVphy_HdmiRxClkDetFreqChangeHandler(XVphy *InstancePtr)
|
|||
XVPHY_GT_STATE_IDLE;
|
||||
}
|
||||
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, TRUE);
|
||||
}
|
||||
|
||||
/* Determine PLL type and RX reference clock selection. */
|
||||
PllType = XVphy_GetPllType(InstancePtr, 0, XVPHY_DIR_RX,
|
||||
XVPHY_CHANNEL_ID_CH1);
|
||||
|
@ -572,17 +645,9 @@ void XVphy_HdmiRxClkDetFreqChangeHandler(XVphy *InstancePtr)
|
|||
/* If the RX frequency has changed, the PLL is always disabled. */
|
||||
XVphy_PowerDownGtPll(InstancePtr, 0, (PllType == XVPHY_PLL_TYPE_CPLL) ?
|
||||
XVPHY_CHANNEL_ID_CHA : XVPHY_CHANNEL_ID_CMNA, TRUE);
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTHE3) {
|
||||
XVphy_ResetGtPll(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, 1);
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, FALSE);
|
||||
XVphy_BufgGtReset(InstancePtr, XVPHY_DIR_RX,TRUE);
|
||||
}
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_GtUserRdyEnable(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, FALSE);
|
||||
}
|
||||
|
||||
XVphy_ResetGtPll(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, TRUE);
|
||||
|
||||
/* When the GT TX and RX are coupled, then disable the QPLL. */
|
||||
if (XVphy_IsBonded(InstancePtr, 0, XVPHY_CHANNEL_ID_CH1)) {
|
||||
|
@ -600,6 +665,12 @@ void XVphy_HdmiRxClkDetFreqChangeHandler(XVphy *InstancePtr)
|
|||
XVphy_MmcmPowerDown(InstancePtr, 0, XVPHY_DIR_TX, TRUE);
|
||||
}
|
||||
|
||||
/* Assert GT RX reset */
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_ResetGtTxRx(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, FALSE);
|
||||
}
|
||||
|
||||
/* If DRU is present, disable it and assert reset. */
|
||||
if (InstancePtr->Config.DruIsPresent) {
|
||||
XVphy_DruReset(InstancePtr, XVPHY_CHANNEL_ID_CHA, TRUE);
|
||||
|
@ -613,9 +684,6 @@ void XVphy_HdmiRxClkDetFreqChangeHandler(XVphy *InstancePtr)
|
|||
if (XVphy_ClkDetGetRefClkFreqHz(InstancePtr, XVPHY_DIR_RX)) {
|
||||
XVphy_ClkDetTimerLoad(InstancePtr, 0, XVPHY_DIR_RX, 100000);
|
||||
}
|
||||
else {
|
||||
return;
|
||||
}
|
||||
|
||||
/* Callback to re-initialize. */
|
||||
if (InstancePtr->HdmiRxInitCallback) {
|
||||
|
@ -671,10 +739,6 @@ void XVphy_HdmiTxTimerTimeoutHandler(XVphy *InstancePtr)
|
|||
XVphy_WriteCfgRefClkSelReg(InstancePtr, 0);
|
||||
}
|
||||
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_GtUserRdyEnable(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX, TRUE);
|
||||
}
|
||||
XVphy_ClkReconfig(InstancePtr, 0, ChId);
|
||||
XVphy_OutDivReconfig(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_TX);
|
||||
|
@ -701,8 +765,6 @@ void XVphy_HdmiTxTimerTimeoutHandler(XVphy *InstancePtr)
|
|||
XVPHY_DIR_TX, FALSE);
|
||||
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTHE3) {
|
||||
XVphy_BufgGtReset(InstancePtr, XVPHY_DIR_TX,FALSE);
|
||||
|
||||
/* Clear GT alignment. */
|
||||
XVphy_TxAlignStart(InstancePtr, ChId, FALSE);
|
||||
}
|
||||
|
@ -807,14 +869,6 @@ void XVphy_HdmiRxTimerTimeoutHandler(XVphy *InstancePtr)
|
|||
|
||||
XVphy_DirReconfig(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA, XVPHY_DIR_RX);
|
||||
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTHE3) {
|
||||
XVphy_BufgGtReset(InstancePtr, XVPHY_DIR_RX,FALSE);
|
||||
}
|
||||
if (InstancePtr->Config.XcvrType == XVPHY_GT_TYPE_GTXE2) {
|
||||
XVphy_GtUserRdyEnable(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA,
|
||||
XVPHY_DIR_RX, TRUE);
|
||||
}
|
||||
|
||||
/* Assert RX PLL reset. */
|
||||
XVphy_ResetGtPll(InstancePtr, 0, XVPHY_CHANNEL_ID_CHA, XVPHY_DIR_RX,
|
||||
TRUE);
|
||||
|
@ -883,11 +937,9 @@ void XVphy_HdmiGtHandler(XVphy *InstancePtr)
|
|||
|
||||
if ((Event & XVPHY_INTR_QPLL0_LOCK_MASK) ||
|
||||
(Event & XVPHY_INTR_QPLL1_LOCK_MASK)){
|
||||
XVphy_WaitUs(InstancePtr, 10 * 1000); //de-bounce lock
|
||||
XVphy_HdmiQpllLockHandler(InstancePtr);
|
||||
}
|
||||
if (Event & XVPHY_INTR_CPLL_LOCK_MASK) {
|
||||
XVphy_WaitUs(InstancePtr, 10 * 1000); //de-bounce lock
|
||||
XVphy_HdmiCpllLockHandler(InstancePtr);
|
||||
}
|
||||
if ((Event & XVPHY_INTR_TXRESETDONE_MASK)
|
||||
|
|
Loading…
Add table
Reference in a new issue