From: Jan Dąbroś jsd@semihalf.com
UTMI PHY must be configured properly in order to enable USB2.0 usage on platforms.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Documentation/Marvell/PortingGuide/Utmi.txt | 35 ++ Platforms/Marvell/Include/Library/UtmiPhyLib.h | 43 +++ Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.c | 353 +++++++++++++++++++++ Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.h | 110 +++++++ .../Marvell/Library/UtmiPhyLib/UtmiPhyLib.inf | 64 ++++ Platforms/Marvell/Marvell.dec | 7 + 6 files changed, 612 insertions(+) create mode 100644 Documentation/Marvell/PortingGuide/Utmi.txt create mode 100644 Platforms/Marvell/Include/Library/UtmiPhyLib.h create mode 100644 Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.c create mode 100644 Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.h create mode 100644 Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.inf
diff --git a/Documentation/Marvell/PortingGuide/Utmi.txt b/Documentation/Marvell/PortingGuide/Utmi.txt new file mode 100644 index 0000000..cff4843 --- /dev/null +++ b/Documentation/Marvell/PortingGuide/Utmi.txt @@ -0,0 +1,35 @@ +UTMI PHY configuration +---------------------- +In order to configure UTMI, following PCDs are available: + + gMarvellTokenSpaceGuid.PcdUtmiPhyCount + +Indicates how many UTMI PHYs are available on platform. + +Next four PCDs are in unicode string format containing settings for all devices +separated with semicolon. + + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiUnit + +Indicates base address of the UTMI unit. + + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUsbCfg + +Indicates address of USB Configuration register. + + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiCfg + +Indicates address of external UTMI configuration. + + gMarvellTokenSpaceGuid.PcdUtmiPhyUtmiPort + +Indicates type of the connected USB port. + +Example +------- +#UtmiPhy + gMarvellTokenSpaceGuid.PcdUtmiPhyCount|2 + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiUnit|L"0xF2580000;0xF2581000" + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUsbCfg|L"0xF2440420;0xF2440420" + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiCfg|L"0xF2440440;0xF2440444" + gMarvellTokenSpaceGuid.PcdUtmiPhyUtmiPort|L"0x0;0x1" diff --git a/Platforms/Marvell/Include/Library/UtmiPhyLib.h b/Platforms/Marvell/Include/Library/UtmiPhyLib.h new file mode 100644 index 0000000..7c62cba --- /dev/null +++ b/Platforms/Marvell/Include/Library/UtmiPhyLib.h @@ -0,0 +1,43 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#ifndef __UTMIPHYLIB_H__ +#define __UTMIPHYLIB_H__ + +EFI_STATUS +UtmiPhyInit ( + VOID + ); + +#endif diff --git a/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.c b/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.c new file mode 100644 index 0000000..985b594 --- /dev/null +++ b/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.c @@ -0,0 +1,353 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must Retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#include "UtmiPhyLib.h" + +typedef struct { + EFI_PHYSICAL_ADDRESS UtmiBaseAddr; + EFI_PHYSICAL_ADDRESS UsbCfgAddr; + EFI_PHYSICAL_ADDRESS UtmiCfgAddr; + UINT32 UtmiPhyPort; +} UTMI_PHY_DATA; + +STATIC +VOID +RegSetSilent ( + IN EFI_PHYSICAL_ADDRESS Addr, + IN UINT32 Data, + IN UINT32 Mask + ) +{ + UINT32 RegData; + + RegData = MmioRead32 (Addr); + RegData &= ~Mask; + RegData |= Data; + MmioWrite32 (Addr, RegData); +} + +STATIC +VOID +RegSet ( + IN EFI_PHYSICAL_ADDRESS Addr, + IN UINT32 Data, + IN UINT32 Mask + ) +{ + DEBUG((DEBUG_INFO, "Write to address = %10x, data = %10x (mask = %10x)-\n", + Addr, Data, Mask)); + DEBUG((DEBUG_INFO, "old value = %10x ==>\n", MmioRead32 (Addr))); + RegSetSilent (Addr, Data, Mask); + DEBUG((DEBUG_INFO, "new value %10x\n", MmioRead32 (Addr))); +} + +STATIC +VOID +UtmiPhyPowerDown ( + IN UINT32 UtmiIndex, + IN EFI_PHYSICAL_ADDRESS UtmiBaseAddr, + IN EFI_PHYSICAL_ADDRESS UsbCfgAddr, + IN EFI_PHYSICAL_ADDRESS UtmiCfgAddr, + IN UINT32 UtmiPhyPort + ) +{ + UINT32 Mask, Data; + + DEBUG((DEBUG_INFO, "UtmiPhy: stage: UTMI %d - Power down transceiver(power down Phy)\n", + UtmiIndex)); + DEBUG((DEBUG_INFO, "UtmiPhy: stage: Power down PLL, and SuspendDM\n")); + /* Power down UTMI PHY */ + RegSet (UtmiCfgAddr, 0x0 << UTMI_PHY_CFG_PU_OFFSET, UTMI_PHY_CFG_PU_MASK); + /* Config USB3 Device UTMI enable */ + Mask = UTMI_USB_CFG_DEVICE_EN_MASK; + + /* + * Prior to PHY init, configure mux for Device + * (Device can be connected to UTMI0 or to UTMI1) + */ + if (UtmiPhyPort == UTMI_PHY_TO_USB_DEVICE0) { + Data = 0x1 << UTMI_USB_CFG_DEVICE_EN_OFFSET; + /* Config USB3 Device UTMI MUX */ + Mask |= UTMI_USB_CFG_DEVICE_MUX_MASK; + Data |= UtmiIndex << UTMI_USB_CFG_DEVICE_MUX_OFFSET; + } else { + Data = 0x0 << UTMI_USB_CFG_DEVICE_EN_OFFSET; + } + + /* Set Test suspendm mode */ + Mask = UTMI_CTRL_STATUS0_SUSPENDM_MASK; + Data = 0x1 << UTMI_CTRL_STATUS0_SUSPENDM_OFFSET; + /* Enable Test UTMI select */ + Mask |= UTMI_CTRL_STATUS0_TEST_SEL_MASK; + Data |= 0x1 << UTMI_CTRL_STATUS0_TEST_SEL_OFFSET; + RegSet (UtmiBaseAddr + UTMI_CTRL_STATUS0_REG, Data, Mask); + + /* Wait for UTMI power down */ + MicroSecondDelay (1000); +} + +STATIC +VOID +UtmiPhyConfig ( + IN UINT32 UtmiIndex, + IN EFI_PHYSICAL_ADDRESS UtmiBaseAddr, + IN EFI_PHYSICAL_ADDRESS UsbCfgAddr, + IN EFI_PHYSICAL_ADDRESS UtmiCfgAddr, + IN UINT32 UtmiPhyPort + ) +{ + UINT32 Mask, Data; + + DEBUG((DEBUG_INFO, "UtmiPhy: stage: Configure UTMI PHY %d registers\n", + UtmiIndex)); + /* Reference Clock Divider Select */ + Mask = UTMI_PLL_CTRL_REFDIV_MASK; + Data = 0x5 << UTMI_PLL_CTRL_REFDIV_OFFSET; + /* Feedback Clock Divider Select - 90 for 25Mhz*/ + Mask |= UTMI_PLL_CTRL_FBDIV_MASK; + Data |= 0x60 << UTMI_PLL_CTRL_FBDIV_OFFSET; + /* Select LPFR - 0x0 for 25Mhz/5=5Mhz */ + Mask |= UTMI_PLL_CTRL_SEL_LPFR_MASK; + Data |= 0x0 << UTMI_PLL_CTRL_SEL_LPFR_OFFSET; + RegSet (UtmiBaseAddr + UTMI_PLL_CTRL_REG, Data, Mask); + + /* Impedance Calibration Threshold Setting */ + RegSet (UtmiBaseAddr + UTMI_CALIB_CTRL_REG, + 0x6 << UTMI_CALIB_CTRL_IMPCAL_VTH_OFFSET, + UTMI_CALIB_CTRL_IMPCAL_VTH_MASK); + + /* Set LS TX driver strength coarse control */ + Mask = UTMI_TX_CH_CTRL_DRV_EN_LS_MASK; + Data = 0x3 << UTMI_TX_CH_CTRL_DRV_EN_LS_OFFSET; + /* Set LS TX driver fine adjustment */ + Mask |= UTMI_TX_CH_CTRL_IMP_SEL_LS_MASK; + Data |= 0x3 << UTMI_TX_CH_CTRL_IMP_SEL_LS_OFFSET; + RegSet (UtmiBaseAddr + UTMI_TX_CH_CTRL_REG, Data, Mask); + + /* Enable SQ */ + Mask = UTMI_RX_CH_CTRL0_SQ_DET_MASK; + Data = 0x0 << UTMI_RX_CH_CTRL0_SQ_DET_OFFSET; + /* Enable analog squelch detect */ + Mask |= UTMI_RX_CH_CTRL0_SQ_ANA_DTC_MASK; + Data |= 0x1 << UTMI_RX_CH_CTRL0_SQ_ANA_DTC_OFFSET; + RegSet (UtmiBaseAddr + UTMI_RX_CH_CTRL0_REG, Data, Mask); + + /* Set External squelch calibration number */ + Mask = UTMI_RX_CH_CTRL1_SQ_AMP_CAL_MASK; + Data = 0x1 << UTMI_RX_CH_CTRL1_SQ_AMP_CAL_OFFSET; + /* Enable the External squelch calibration */ + Mask |= UTMI_RX_CH_CTRL1_SQ_AMP_CAL_EN_MASK; + Data |= 0x1 << UTMI_RX_CH_CTRL1_SQ_AMP_CAL_EN_OFFSET; + RegSet (UtmiBaseAddr + UTMI_RX_CH_CTRL1_REG, Data, Mask); + + /* Set Control VDAT Reference Voltage - 0.325V */ + Mask = UTMI_CHGDTC_CTRL_VDAT_MASK; + Data = 0x1 << UTMI_CHGDTC_CTRL_VDAT_OFFSET; + /* Set Control VSRC Reference Voltage - 0.6V */ + Mask |= UTMI_CHGDTC_CTRL_VSRC_MASK; + Data |= 0x1 << UTMI_CHGDTC_CTRL_VSRC_OFFSET; + RegSet (UtmiBaseAddr + UTMI_CHGDTC_CTRL_REG, Data, Mask); +} + +STATIC +UINTN +UtmiPhyPowerUp ( + IN UINT32 UtmiIndex, + IN EFI_PHYSICAL_ADDRESS UtmiBaseAddr, + IN EFI_PHYSICAL_ADDRESS UsbCfgAddr, + IN EFI_PHYSICAL_ADDRESS UtmiCfgAddr, + IN UINT32 UtmiPhyPort + ) +{ + EFI_STATUS Status; + UINT32 Data; + + DEBUG((DEBUG_INFO, "UtmiPhy: stage: UTMI %d - Power up transceiver(Power up Phy)\n", + UtmiIndex)); + DEBUG((DEBUG_INFO, "UtmiPhy: stage: exit SuspendDM\n")); + /* Power up UTMI PHY */ + RegSet (UtmiCfgAddr, 0x1 << UTMI_PHY_CFG_PU_OFFSET, UTMI_PHY_CFG_PU_MASK); + /* Disable Test UTMI select */ + RegSet (UtmiBaseAddr + UTMI_CTRL_STATUS0_REG, + 0x0 << UTMI_CTRL_STATUS0_TEST_SEL_OFFSET, + UTMI_CTRL_STATUS0_TEST_SEL_MASK); + + DEBUG((DEBUG_INFO, "UtmiPhy: stage: Wait for PLL and impedance calibration done, and PLL ready\n")); + + /* Delay 10ms */ + MicroSecondDelay (10000); + + Data = MmioRead32 (UtmiBaseAddr + UTMI_CALIB_CTRL_REG); + if ((Data & UTMI_CALIB_CTRL_IMPCAL_DONE_MASK) == 0) { + DEBUG((DEBUG_ERROR, "UtmiPhy: Impedance calibration is not done\n")); + Status = EFI_D_ERROR; + } + if ((Data & UTMI_CALIB_CTRL_PLLCAL_DONE_MASK) == 0) { + DEBUG((DEBUG_ERROR, "UtmiPhy: PLL calibration is not done\n")); + Status = EFI_D_ERROR; + } + Data = MmioRead32 (UtmiBaseAddr + UTMI_PLL_CTRL_REG); + if ((Data & UTMI_PLL_CTRL_PLL_RDY_MASK) == 0) { + DEBUG((DEBUG_ERROR, "UtmiPhy: PLL is not ready\n")); + Status = EFI_D_ERROR; + } + + return Status; +} + +/* + * Cp110UtmiPhyInit initializes the UTMI PHY + * the init split in 3 parts: + * 1. Power down transceiver and PLL + * 2. UTMI PHY configure + * 3. Power up transceiver and PLL + */ +STATIC +VOID +Cp110UtmiPhyInit ( + IN UINT32 UtmiPhyCount, + IN UTMI_PHY_DATA *UtmiData + ) +{ + UINT32 i; + + for (i = 0; i < UtmiPhyCount; i++) { + UtmiPhyPowerDown(i, UtmiData[i].UtmiBaseAddr, + UtmiData[i].UsbCfgAddr, UtmiData[i].UtmiCfgAddr, + UtmiData[i].UtmiPhyPort); + } + + /* Power down PLL */ + DEBUG((DEBUG_INFO, "UtmiPhy: stage: PHY power down PLL\n")); + RegSet (UtmiData[0].UsbCfgAddr, 0x0 << UTMI_USB_CFG_PLL_OFFSET, + UTMI_USB_CFG_PLL_MASK); + + for (i = 0; i < UtmiPhyCount; i++) { + UtmiPhyConfig(i, UtmiData[i].UtmiBaseAddr, + UtmiData[i].UsbCfgAddr, UtmiData[i].UtmiCfgAddr, + UtmiData[i].UtmiPhyPort); + } + + for (i = 0; i < UtmiPhyCount; i++) { + if (EFI_ERROR(UtmiPhyPowerUp(i, UtmiData[i].UtmiBaseAddr, + UtmiData[i].UsbCfgAddr, UtmiData[i].UtmiCfgAddr, + UtmiData[i].UtmiPhyPort))) { + DEBUG((DEBUG_ERROR, "UtmiPhy: Failed to initialize UTMI PHY %d\n", i)); + continue; + } + DEBUG((DEBUG_ERROR, "UTMI PHY %d initialized to ", i)); + + if (UtmiData[i].UtmiPhyPort == UTMI_PHY_TO_USB_DEVICE0) + DEBUG((DEBUG_ERROR, "USB Device\n")); + else + DEBUG((DEBUG_ERROR, "USB Host%d\n", UtmiData[i].UtmiPhyPort)); + } + + /* Power up PLL */ + DEBUG((DEBUG_INFO, "UtmiPhy: stage: PHY power up PLL\n")); + RegSet (UtmiData[0].UsbCfgAddr, 0x1 << UTMI_USB_CFG_PLL_OFFSET, + UTMI_USB_CFG_PLL_MASK); +} + +EFI_STATUS +UtmiPhyInit ( + VOID + ) +{ + EFI_STATUS Status; + UTMI_PHY_DATA UtmiData[PcdGet32 (PcdUtmiPhyCount)]; + EFI_PHYSICAL_ADDRESS RegUtmiUnit[PcdGet32 (PcdUtmiPhyCount)]; + EFI_PHYSICAL_ADDRESS RegUsbCfg[PcdGet32 (PcdUtmiPhyCount)]; + EFI_PHYSICAL_ADDRESS RegUtmiCfg[PcdGet32 (PcdUtmiPhyCount)]; + UINTN UtmiPort[PcdGet32 (PcdUtmiPhyCount)]; + UINTN i, Count; + + Count = PcdGet32 (PcdUtmiPhyCount); + if (Count == 0) { + /* No UTMI PHY on platform */ + return EFI_SUCCESS; + } + + DEBUG((DEBUG_INFO, "UtmiPhy: Initialize USB UTMI PHYs\n")); + /* Parse UtmiPhy PCDs */ + Status = ParsePcdString ((CHAR16 *) PcdGetPtr (PcdUtmiPhyRegUtmiUnit), + Count, RegUtmiUnit, NULL); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "UtmiPhy: Wrong PcdUtmiPhyRegUtmiUnit format\n")); + return EFI_INVALID_PARAMETER; + } + + Status = ParsePcdString ((CHAR16 *) PcdGetPtr (PcdUtmiPhyRegUsbCfg), + Count, RegUsbCfg, NULL); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "UtmiPhy: Wrong PcdUtmiPhyRegUsbCfg format\n")); + return EFI_INVALID_PARAMETER; + } + + Status = ParsePcdString ((CHAR16 *) PcdGetPtr (PcdUtmiPhyRegUtmiCfg), + Count, RegUtmiCfg, NULL); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "UtmiPhy: Wrong PcdUtmiPhyRegUtmiCfg format\n")); + return EFI_INVALID_PARAMETER; + } + + Status = ParsePcdString ((CHAR16 *) PcdGetPtr (PcdUtmiPhyUtmiPort), + Count, UtmiPort, NULL); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "UtmiPhy: Wrong PcdUtmiPhyUtmiPort format\n")); + return EFI_INVALID_PARAMETER; + } + + for (i = 0 ; i < Count ; i++) { + /* Get base address of UTMI phy */ + UtmiData[i].UtmiBaseAddr = RegUtmiUnit[i]; + + /* Get usb config address */ + UtmiData[i].UsbCfgAddr = RegUsbCfg[i]; + + /* Get UTMI config address */ + UtmiData[i].UtmiCfgAddr = RegUtmiCfg[i]; + + /* + * Get the usb port number, which will be used to check if + * the utmi connected to host or device + */ + UtmiData[i].UtmiPhyPort = UtmiPort[i]; + } + + /* Currently only Cp110 is supported */ + Cp110UtmiPhyInit (Count, UtmiData); + + return EFI_SUCCESS; +} diff --git a/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.h b/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.h new file mode 100644 index 0000000..f9b4933 --- /dev/null +++ b/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.h @@ -0,0 +1,110 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#ifndef __UTMIPHY_H__ +#define __UTMIPHY_H__ + +#include <Library/ArmLib.h> +#include <Library/ArmPlatformLib.h> +#include <Library/DebugLib.h> +#include <Library/PcdLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/IoLib.h> +#include <Library/TimerLib.h> +#include <Library/ParsePcdLib.h> + +#define UTMI_USB_CFG_DEVICE_EN_OFFSET 0 +#define UTMI_USB_CFG_DEVICE_EN_MASK (0x1 << UTMI_USB_CFG_DEVICE_EN_OFFSET) +#define UTMI_USB_CFG_DEVICE_MUX_OFFSET 1 +#define UTMI_USB_CFG_DEVICE_MUX_MASK (0x1 << UTMI_USB_CFG_DEVICE_MUX_OFFSET) +#define UTMI_USB_CFG_PLL_OFFSET 25 +#define UTMI_USB_CFG_PLL_MASK (0x1 << UTMI_USB_CFG_PLL_OFFSET) + +#define UTMI_PHY_CFG_PU_OFFSET 5 +#define UTMI_PHY_CFG_PU_MASK (0x1 << UTMI_PHY_CFG_PU_OFFSET) + +#define UTMI_PLL_CTRL_REG 0x0 +#define UTMI_PLL_CTRL_REFDIV_OFFSET 0 +#define UTMI_PLL_CTRL_REFDIV_MASK (0x7f << UTMI_PLL_CTRL_REFDIV_OFFSET) +#define UTMI_PLL_CTRL_FBDIV_OFFSET 16 +#define UTMI_PLL_CTRL_FBDIV_MASK (0x1FF << UTMI_PLL_CTRL_FBDIV_OFFSET) +#define UTMI_PLL_CTRL_SEL_LPFR_OFFSET 28 +#define UTMI_PLL_CTRL_SEL_LPFR_MASK (0x3 << UTMI_PLL_CTRL_SEL_LPFR_OFFSET) +#define UTMI_PLL_CTRL_PLL_RDY_OFFSET 31 +#define UTMI_PLL_CTRL_PLL_RDY_MASK (0x1 << UTMI_PLL_CTRL_PLL_RDY_OFFSET) + +#define UTMI_CALIB_CTRL_REG 0x8 +#define UTMI_CALIB_CTRL_IMPCAL_VTH_OFFSET 8 +#define UTMI_CALIB_CTRL_IMPCAL_VTH_MASK (0x7 << UTMI_CALIB_CTRL_IMPCAL_VTH_OFFSET) +#define UTMI_CALIB_CTRL_IMPCAL_DONE_OFFSET 23 +#define UTMI_CALIB_CTRL_IMPCAL_DONE_MASK (0x1 << UTMI_CALIB_CTRL_IMPCAL_DONE_OFFSET) +#define UTMI_CALIB_CTRL_PLLCAL_DONE_OFFSET 31 +#define UTMI_CALIB_CTRL_PLLCAL_DONE_MASK (0x1 << UTMI_CALIB_CTRL_PLLCAL_DONE_OFFSET) + +#define UTMI_TX_CH_CTRL_REG 0xC +#define UTMI_TX_CH_CTRL_DRV_EN_LS_OFFSET 12 +#define UTMI_TX_CH_CTRL_DRV_EN_LS_MASK (0xf << UTMI_TX_CH_CTRL_DRV_EN_LS_OFFSET) +#define UTMI_TX_CH_CTRL_IMP_SEL_LS_OFFSET 16 +#define UTMI_TX_CH_CTRL_IMP_SEL_LS_MASK (0xf << UTMI_TX_CH_CTRL_IMP_SEL_LS_OFFSET) + +#define UTMI_RX_CH_CTRL0_REG 0x14 +#define UTMI_RX_CH_CTRL0_SQ_DET_OFFSET 15 +#define UTMI_RX_CH_CTRL0_SQ_DET_MASK (0x1 << UTMI_RX_CH_CTRL0_SQ_DET_OFFSET) +#define UTMI_RX_CH_CTRL0_SQ_ANA_DTC_OFFSET 28 +#define UTMI_RX_CH_CTRL0_SQ_ANA_DTC_MASK (0x1 << UTMI_RX_CH_CTRL0_SQ_ANA_DTC_OFFSET) + +#define UTMI_RX_CH_CTRL1_REG 0x18 +#define UTMI_RX_CH_CTRL1_SQ_AMP_CAL_OFFSET 0 +#define UTMI_RX_CH_CTRL1_SQ_AMP_CAL_MASK (0x3 << UTMI_RX_CH_CTRL1_SQ_AMP_CAL_OFFSET) +#define UTMI_RX_CH_CTRL1_SQ_AMP_CAL_EN_OFFSET 3 +#define UTMI_RX_CH_CTRL1_SQ_AMP_CAL_EN_MASK (0x1 << UTMI_RX_CH_CTRL1_SQ_AMP_CAL_EN_OFFSET) + +#define UTMI_CTRL_STATUS0_REG 0x24 +#define UTMI_CTRL_STATUS0_SUSPENDM_OFFSET 22 +#define UTMI_CTRL_STATUS0_SUSPENDM_MASK (0x1 << UTMI_CTRL_STATUS0_SUSPENDM_OFFSET) +#define UTMI_CTRL_STATUS0_TEST_SEL_OFFSET 25 +#define UTMI_CTRL_STATUS0_TEST_SEL_MASK (0x1 << UTMI_CTRL_STATUS0_TEST_SEL_OFFSET) + +#define UTMI_CHGDTC_CTRL_REG 0x38 +#define UTMI_CHGDTC_CTRL_VDAT_OFFSET 8 +#define UTMI_CHGDTC_CTRL_VDAT_MASK (0x3 << UTMI_CHGDTC_CTRL_VDAT_OFFSET) +#define UTMI_CHGDTC_CTRL_VSRC_OFFSET 10 +#define UTMI_CHGDTC_CTRL_VSRC_MASK (0x3 << UTMI_CHGDTC_CTRL_VSRC_OFFSET) + +#define UTMI_PHY_TO_USB_HOST0 0 +#define UTMI_PHY_TO_USB_HOST1 1 +#define UTMI_PHY_TO_USB_DEVICE0 2 +#define UTMI_PHY_INVALID 0xff + +#endif diff --git a/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.inf b/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.inf new file mode 100644 index 0000000..21de609 --- /dev/null +++ b/Platforms/Marvell/Library/UtmiPhyLib/UtmiPhyLib.inf @@ -0,0 +1,64 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + INF_VERSION = 0x00010019 + BASE_NAME = MarvellUtmiPhyLib + FILE_GUID = e9adaac2-0443-4921-9367-5d575c3c91bc + MODULE_TYPE = BASE + VERSION_STRING = 1.0 + LIBRARY_CLASS = UtmiPhyLib + +[Packages] + ArmPkg/ArmPkg.dec + ArmPlatformPkg/ArmPlatformPkg.dec + MdeModulePkg/MdeModulePkg.dec + MdePkg/MdePkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + ArmLib + DebugLib + IoLib + MemoryAllocationLib + ParsePcdLib + PcdLib + +[Sources.common] + UtmiPhyLib.c + +[FixedPcd] + gMarvellTokenSpaceGuid.PcdUtmiPhyCount + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUsbCfg + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiCfg + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiUnit + gMarvellTokenSpaceGuid.PcdUtmiPhyUtmiPort diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index 73102ed..31236a3 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -178,6 +178,13 @@ #SATA gMarvellTokenSpaceGuid.PcdSataBaseAddress|0|UINT32|0x4000052
+#UtmiPhy + gMarvellTokenSpaceGuid.PcdUtmiPhyCount|0|UINT32|0x30000205 + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUsbCfg|{ 0 }|VOID*|0x30000206 + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiCfg|{ 0 }|VOID*|0x30000207 + gMarvellTokenSpaceGuid.PcdUtmiPhyRegUtmiUnit|{ 0 }|VOID*|0x30000208 + gMarvellTokenSpaceGuid.PcdUtmiPhyUtmiPort|{ 0 }|VOID*|0x30000209 + #MDIO gMarvellTokenSpaceGuid.PcdMdioBaseAddress|0|UINT64|0x3000043