Zeroday Hong / mbed-dev

Fork of mbed-dev by mbed official

Committer:
<>
Date:
Wed Jan 04 16:58:05 2017 +0000
Revision:
154:37f96f9d4de2
This updates the lib to the mbed lib v133

Who changed what in which revision?

UserRevisionLine numberNew contents of line
<> 154:37f96f9d4de2 1 /*
<> 154:37f96f9d4de2 2 * Copyright (c) 2015, Freescale Semiconductor, Inc.
<> 154:37f96f9d4de2 3 * All rights reserved.
<> 154:37f96f9d4de2 4 *
<> 154:37f96f9d4de2 5 * Redistribution and use in source and binary forms, with or without modification,
<> 154:37f96f9d4de2 6 * are permitted provided that the following conditions are met:
<> 154:37f96f9d4de2 7 *
<> 154:37f96f9d4de2 8 * o Redistributions of source code must retain the above copyright notice, this list
<> 154:37f96f9d4de2 9 * of conditions and the following disclaimer.
<> 154:37f96f9d4de2 10 *
<> 154:37f96f9d4de2 11 * o Redistributions in binary form must reproduce the above copyright notice, this
<> 154:37f96f9d4de2 12 * list of conditions and the following disclaimer in the documentation and/or
<> 154:37f96f9d4de2 13 * other materials provided with the distribution.
<> 154:37f96f9d4de2 14 *
<> 154:37f96f9d4de2 15 * o Neither the name of Freescale Semiconductor, Inc. nor the names of its
<> 154:37f96f9d4de2 16 * contributors may be used to endorse or promote products derived from this
<> 154:37f96f9d4de2 17 * software without specific prior written permission.
<> 154:37f96f9d4de2 18 *
<> 154:37f96f9d4de2 19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
<> 154:37f96f9d4de2 20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
<> 154:37f96f9d4de2 21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
<> 154:37f96f9d4de2 22 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
<> 154:37f96f9d4de2 23 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
<> 154:37f96f9d4de2 24 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
<> 154:37f96f9d4de2 25 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
<> 154:37f96f9d4de2 26 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
<> 154:37f96f9d4de2 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
<> 154:37f96f9d4de2 28 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
<> 154:37f96f9d4de2 29 */
<> 154:37f96f9d4de2 30
<> 154:37f96f9d4de2 31 #include "fsl_phy.h"
<> 154:37f96f9d4de2 32
<> 154:37f96f9d4de2 33 /*******************************************************************************
<> 154:37f96f9d4de2 34 * Definitions
<> 154:37f96f9d4de2 35 ******************************************************************************/
<> 154:37f96f9d4de2 36
<> 154:37f96f9d4de2 37 /*! @brief Defines the timeout macro. */
<> 154:37f96f9d4de2 38 #define PHY_TIMEOUT_COUNT 0xFFFFFU
<> 154:37f96f9d4de2 39
<> 154:37f96f9d4de2 40 /*******************************************************************************
<> 154:37f96f9d4de2 41 * Prototypes
<> 154:37f96f9d4de2 42 ******************************************************************************/
<> 154:37f96f9d4de2 43
<> 154:37f96f9d4de2 44 /*!
<> 154:37f96f9d4de2 45 * @brief Get the ENET instance from peripheral base address.
<> 154:37f96f9d4de2 46 *
<> 154:37f96f9d4de2 47 * @param base ENET peripheral base address.
<> 154:37f96f9d4de2 48 * @return ENET instance.
<> 154:37f96f9d4de2 49 */
<> 154:37f96f9d4de2 50 extern uint32_t ENET_GetInstance(ENET_Type *base);
<> 154:37f96f9d4de2 51
<> 154:37f96f9d4de2 52 /*******************************************************************************
<> 154:37f96f9d4de2 53 * Variables
<> 154:37f96f9d4de2 54 ******************************************************************************/
<> 154:37f96f9d4de2 55
<> 154:37f96f9d4de2 56 /*! @brief Pointers to enet clocks for each instance. */
<> 154:37f96f9d4de2 57 extern clock_ip_name_t s_enetClock[FSL_FEATURE_SOC_ENET_COUNT];
<> 154:37f96f9d4de2 58
<> 154:37f96f9d4de2 59 /*******************************************************************************
<> 154:37f96f9d4de2 60 * Code
<> 154:37f96f9d4de2 61 ******************************************************************************/
<> 154:37f96f9d4de2 62
<> 154:37f96f9d4de2 63 status_t PHY_Init(ENET_Type *base, uint32_t phyAddr, uint32_t srcClock_Hz)
<> 154:37f96f9d4de2 64 {
<> 154:37f96f9d4de2 65 uint32_t bssReg;
<> 154:37f96f9d4de2 66 uint32_t counter = PHY_TIMEOUT_COUNT;
<> 154:37f96f9d4de2 67 status_t result = kStatus_Success;
<> 154:37f96f9d4de2 68 uint32_t instance = ENET_GetInstance(base);
<> 154:37f96f9d4de2 69
<> 154:37f96f9d4de2 70 /* Set SMI first. */
<> 154:37f96f9d4de2 71 CLOCK_EnableClock(s_enetClock[instance]);
<> 154:37f96f9d4de2 72 ENET_SetSMI(base, srcClock_Hz, false);
<> 154:37f96f9d4de2 73
<> 154:37f96f9d4de2 74 /* Reset PHY. */
<> 154:37f96f9d4de2 75 result = PHY_Write(base, phyAddr, PHY_BASICCONTROL_REG, PHY_BCTL_RESET_MASK);
<> 154:37f96f9d4de2 76 if (result == kStatus_Success)
<> 154:37f96f9d4de2 77 {
<> 154:37f96f9d4de2 78 /* Set the negotiation. */
<> 154:37f96f9d4de2 79 result = PHY_Write(base, phyAddr, PHY_AUTONEG_ADVERTISE_REG,
<> 154:37f96f9d4de2 80 (PHY_100BASETX_FULLDUPLEX_MASK | PHY_100BASETX_HALFDUPLEX_MASK |
<> 154:37f96f9d4de2 81 PHY_10BASETX_FULLDUPLEX_MASK | PHY_10BASETX_HALFDUPLEX_MASK | 0x1U));
<> 154:37f96f9d4de2 82 if (result == kStatus_Success)
<> 154:37f96f9d4de2 83 {
<> 154:37f96f9d4de2 84 result = PHY_Write(base, phyAddr, PHY_BASICCONTROL_REG,
<> 154:37f96f9d4de2 85 (PHY_BCTL_AUTONEG_MASK | PHY_BCTL_RESTART_AUTONEG_MASK));
<> 154:37f96f9d4de2 86 if (result == kStatus_Success)
<> 154:37f96f9d4de2 87 {
<> 154:37f96f9d4de2 88 /* Check auto negotiation complete. */
<> 154:37f96f9d4de2 89 while (counter --)
<> 154:37f96f9d4de2 90 {
<> 154:37f96f9d4de2 91 result = PHY_Read(base, phyAddr, PHY_BASICSTATUS_REG, &bssReg);
<> 154:37f96f9d4de2 92 if ( result == kStatus_Success)
<> 154:37f96f9d4de2 93 {
<> 154:37f96f9d4de2 94 if ((bssReg & PHY_BSTATUS_AUTONEGCOMP_MASK) != 0)
<> 154:37f96f9d4de2 95 {
<> 154:37f96f9d4de2 96 break;
<> 154:37f96f9d4de2 97 }
<> 154:37f96f9d4de2 98 }
<> 154:37f96f9d4de2 99
<> 154:37f96f9d4de2 100 if (!counter)
<> 154:37f96f9d4de2 101 {
<> 154:37f96f9d4de2 102 return kStatus_PHY_AutoNegotiateFail;
<> 154:37f96f9d4de2 103 }
<> 154:37f96f9d4de2 104 }
<> 154:37f96f9d4de2 105 }
<> 154:37f96f9d4de2 106 }
<> 154:37f96f9d4de2 107 }
<> 154:37f96f9d4de2 108
<> 154:37f96f9d4de2 109 return result;
<> 154:37f96f9d4de2 110 }
<> 154:37f96f9d4de2 111
<> 154:37f96f9d4de2 112 status_t PHY_Write(ENET_Type *base, uint32_t phyAddr, uint32_t phyReg, uint32_t data)
<> 154:37f96f9d4de2 113 {
<> 154:37f96f9d4de2 114 uint32_t counter;
<> 154:37f96f9d4de2 115
<> 154:37f96f9d4de2 116 /* Clear the SMI interrupt event. */
<> 154:37f96f9d4de2 117 ENET_ClearInterruptStatus(base, ENET_EIR_MII_MASK);
<> 154:37f96f9d4de2 118
<> 154:37f96f9d4de2 119 /* Starts a SMI write command. */
<> 154:37f96f9d4de2 120 ENET_StartSMIWrite(base, phyAddr, phyReg, kENET_MiiWriteValidFrame, data);
<> 154:37f96f9d4de2 121
<> 154:37f96f9d4de2 122 /* Wait for SMI complete. */
<> 154:37f96f9d4de2 123 for (counter = PHY_TIMEOUT_COUNT; counter > 0; counter--)
<> 154:37f96f9d4de2 124 {
<> 154:37f96f9d4de2 125 if (ENET_GetInterruptStatus(base) & ENET_EIR_MII_MASK)
<> 154:37f96f9d4de2 126 {
<> 154:37f96f9d4de2 127 break;
<> 154:37f96f9d4de2 128 }
<> 154:37f96f9d4de2 129 }
<> 154:37f96f9d4de2 130
<> 154:37f96f9d4de2 131 /* Check for timeout. */
<> 154:37f96f9d4de2 132 if (!counter)
<> 154:37f96f9d4de2 133 {
<> 154:37f96f9d4de2 134 return kStatus_PHY_SMIVisitTimeout;
<> 154:37f96f9d4de2 135 }
<> 154:37f96f9d4de2 136
<> 154:37f96f9d4de2 137 /* Clear MII interrupt event. */
<> 154:37f96f9d4de2 138 ENET_ClearInterruptStatus(base, ENET_EIR_MII_MASK);
<> 154:37f96f9d4de2 139
<> 154:37f96f9d4de2 140 return kStatus_Success;
<> 154:37f96f9d4de2 141 }
<> 154:37f96f9d4de2 142
<> 154:37f96f9d4de2 143 status_t PHY_Read(ENET_Type *base, uint32_t phyAddr, uint32_t phyReg, uint32_t *dataPtr)
<> 154:37f96f9d4de2 144 {
<> 154:37f96f9d4de2 145 assert(dataPtr);
<> 154:37f96f9d4de2 146
<> 154:37f96f9d4de2 147 uint32_t counter;
<> 154:37f96f9d4de2 148
<> 154:37f96f9d4de2 149 /* Clear the MII interrupt event. */
<> 154:37f96f9d4de2 150 ENET_ClearInterruptStatus(base, ENET_EIR_MII_MASK);
<> 154:37f96f9d4de2 151
<> 154:37f96f9d4de2 152 /* Starts a SMI read command operation. */
<> 154:37f96f9d4de2 153 ENET_StartSMIRead(base, phyAddr, phyReg, kENET_MiiReadValidFrame);
<> 154:37f96f9d4de2 154
<> 154:37f96f9d4de2 155 /* Wait for MII complete. */
<> 154:37f96f9d4de2 156 for (counter = PHY_TIMEOUT_COUNT; counter > 0; counter--)
<> 154:37f96f9d4de2 157 {
<> 154:37f96f9d4de2 158 if (ENET_GetInterruptStatus(base) & ENET_EIR_MII_MASK)
<> 154:37f96f9d4de2 159 {
<> 154:37f96f9d4de2 160 break;
<> 154:37f96f9d4de2 161 }
<> 154:37f96f9d4de2 162 }
<> 154:37f96f9d4de2 163
<> 154:37f96f9d4de2 164 /* Check for timeout. */
<> 154:37f96f9d4de2 165 if (!counter)
<> 154:37f96f9d4de2 166 {
<> 154:37f96f9d4de2 167 return kStatus_PHY_SMIVisitTimeout;
<> 154:37f96f9d4de2 168 }
<> 154:37f96f9d4de2 169
<> 154:37f96f9d4de2 170 /* Get data from MII register. */
<> 154:37f96f9d4de2 171 *dataPtr = ENET_ReadSMIData(base);
<> 154:37f96f9d4de2 172
<> 154:37f96f9d4de2 173 /* Clear MII interrupt event. */
<> 154:37f96f9d4de2 174 ENET_ClearInterruptStatus(base, ENET_EIR_MII_MASK);
<> 154:37f96f9d4de2 175
<> 154:37f96f9d4de2 176 return kStatus_Success;
<> 154:37f96f9d4de2 177 }
<> 154:37f96f9d4de2 178
<> 154:37f96f9d4de2 179 status_t PHY_EnableLoopback(ENET_Type *base, uint32_t phyAddr, phy_loop_t mode, bool enable)
<> 154:37f96f9d4de2 180 {
<> 154:37f96f9d4de2 181 status_t result;
<> 154:37f96f9d4de2 182 uint32_t data = 0;
<> 154:37f96f9d4de2 183
<> 154:37f96f9d4de2 184 /* Set the loop mode. */
<> 154:37f96f9d4de2 185 if (enable)
<> 154:37f96f9d4de2 186 {
<> 154:37f96f9d4de2 187 if (mode == kPHY_LocalLoop)
<> 154:37f96f9d4de2 188 {
<> 154:37f96f9d4de2 189 /* First read the current status in control register. */
<> 154:37f96f9d4de2 190 result = PHY_Read(base, phyAddr, PHY_BASICCONTROL_REG, &data);
<> 154:37f96f9d4de2 191 if (result == kStatus_Success)
<> 154:37f96f9d4de2 192 {
<> 154:37f96f9d4de2 193 return PHY_Write(base, phyAddr, PHY_BASICCONTROL_REG, (data | PHY_BCTL_LOOP_MASK));
<> 154:37f96f9d4de2 194 }
<> 154:37f96f9d4de2 195 }
<> 154:37f96f9d4de2 196 else
<> 154:37f96f9d4de2 197 {
<> 154:37f96f9d4de2 198 /* First read the current status in control register. */
<> 154:37f96f9d4de2 199 result = PHY_Read(base, phyAddr, PHY_CONTROL2_REG, &data);
<> 154:37f96f9d4de2 200 if (result == kStatus_Success)
<> 154:37f96f9d4de2 201 {
<> 154:37f96f9d4de2 202 return PHY_Write(base, phyAddr, PHY_CONTROL2_REG, (data | PHY_CTL2_REMOTELOOP_MASK));
<> 154:37f96f9d4de2 203 }
<> 154:37f96f9d4de2 204 }
<> 154:37f96f9d4de2 205 }
<> 154:37f96f9d4de2 206 else
<> 154:37f96f9d4de2 207 {
<> 154:37f96f9d4de2 208 /* Disable the loop mode. */
<> 154:37f96f9d4de2 209 if (mode == kPHY_LocalLoop)
<> 154:37f96f9d4de2 210 {
<> 154:37f96f9d4de2 211 /* First read the current status in the basic control register. */
<> 154:37f96f9d4de2 212 result = PHY_Read(base, phyAddr, PHY_BASICCONTROL_REG, &data);
<> 154:37f96f9d4de2 213 if (result == kStatus_Success)
<> 154:37f96f9d4de2 214 {
<> 154:37f96f9d4de2 215 return PHY_Write(base, phyAddr, PHY_BASICCONTROL_REG, (data & ~PHY_BCTL_LOOP_MASK));
<> 154:37f96f9d4de2 216 }
<> 154:37f96f9d4de2 217 }
<> 154:37f96f9d4de2 218 else
<> 154:37f96f9d4de2 219 {
<> 154:37f96f9d4de2 220 /* First read the current status in control one register. */
<> 154:37f96f9d4de2 221 result = PHY_Read(base, phyAddr, PHY_CONTROL2_REG, &data);
<> 154:37f96f9d4de2 222 if (result == kStatus_Success)
<> 154:37f96f9d4de2 223 {
<> 154:37f96f9d4de2 224 return PHY_Write(base, phyAddr, PHY_CONTROL2_REG, (data & ~PHY_CTL2_REMOTELOOP_MASK));
<> 154:37f96f9d4de2 225 }
<> 154:37f96f9d4de2 226 }
<> 154:37f96f9d4de2 227 }
<> 154:37f96f9d4de2 228 return result;
<> 154:37f96f9d4de2 229 }
<> 154:37f96f9d4de2 230
<> 154:37f96f9d4de2 231 status_t PHY_GetLinkStatus(ENET_Type *base, uint32_t phyAddr, bool *status)
<> 154:37f96f9d4de2 232 {
<> 154:37f96f9d4de2 233 assert(status);
<> 154:37f96f9d4de2 234
<> 154:37f96f9d4de2 235 status_t result = kStatus_Success;
<> 154:37f96f9d4de2 236 uint32_t data;
<> 154:37f96f9d4de2 237
<> 154:37f96f9d4de2 238 /* Read the basic status register. */
<> 154:37f96f9d4de2 239 result = PHY_Read(base, phyAddr, PHY_BASICSTATUS_REG, &data);
<> 154:37f96f9d4de2 240 if (result == kStatus_Success)
<> 154:37f96f9d4de2 241 {
<> 154:37f96f9d4de2 242 if (!(PHY_BSTATUS_LINKSTATUS_MASK & data))
<> 154:37f96f9d4de2 243 {
<> 154:37f96f9d4de2 244 /* link down. */
<> 154:37f96f9d4de2 245 *status = false;
<> 154:37f96f9d4de2 246 }
<> 154:37f96f9d4de2 247 else
<> 154:37f96f9d4de2 248 {
<> 154:37f96f9d4de2 249 /* link up. */
<> 154:37f96f9d4de2 250 *status = true;
<> 154:37f96f9d4de2 251 }
<> 154:37f96f9d4de2 252 }
<> 154:37f96f9d4de2 253 return result;
<> 154:37f96f9d4de2 254 }
<> 154:37f96f9d4de2 255
<> 154:37f96f9d4de2 256 status_t PHY_GetLinkSpeedDuplex(ENET_Type *base, uint32_t phyAddr, phy_speed_t *speed, phy_duplex_t *duplex)
<> 154:37f96f9d4de2 257 {
<> 154:37f96f9d4de2 258 assert(duplex);
<> 154:37f96f9d4de2 259
<> 154:37f96f9d4de2 260 status_t result = kStatus_Success;
<> 154:37f96f9d4de2 261 uint32_t data, ctlReg;
<> 154:37f96f9d4de2 262
<> 154:37f96f9d4de2 263 /* Read the control two register. */
<> 154:37f96f9d4de2 264 result = PHY_Read(base, phyAddr, PHY_CONTROL1_REG, &ctlReg);
<> 154:37f96f9d4de2 265 if (result == kStatus_Success)
<> 154:37f96f9d4de2 266 {
<> 154:37f96f9d4de2 267 data = ctlReg & PHY_CTL1_SPEEDUPLX_MASK;
<> 154:37f96f9d4de2 268 if ((PHY_CTL1_10FULLDUPLEX_MASK == data) || (PHY_CTL1_100FULLDUPLEX_MASK == data))
<> 154:37f96f9d4de2 269 {
<> 154:37f96f9d4de2 270 /* Full duplex. */
<> 154:37f96f9d4de2 271 *duplex = kPHY_FullDuplex;
<> 154:37f96f9d4de2 272 }
<> 154:37f96f9d4de2 273 else
<> 154:37f96f9d4de2 274 {
<> 154:37f96f9d4de2 275 /* Half duplex. */
<> 154:37f96f9d4de2 276 *duplex = kPHY_HalfDuplex;
<> 154:37f96f9d4de2 277 }
<> 154:37f96f9d4de2 278
<> 154:37f96f9d4de2 279 data = ctlReg & PHY_CTL1_SPEEDUPLX_MASK;
<> 154:37f96f9d4de2 280 if ((PHY_CTL1_100HALFDUPLEX_MASK == data) || (PHY_CTL1_100FULLDUPLEX_MASK == data))
<> 154:37f96f9d4de2 281 {
<> 154:37f96f9d4de2 282 /* 100M speed. */
<> 154:37f96f9d4de2 283 *speed = kPHY_Speed100M;
<> 154:37f96f9d4de2 284 }
<> 154:37f96f9d4de2 285 else
<> 154:37f96f9d4de2 286 { /* 10M speed. */
<> 154:37f96f9d4de2 287 *speed = kPHY_Speed10M;
<> 154:37f96f9d4de2 288 }
<> 154:37f96f9d4de2 289 }
<> 154:37f96f9d4de2 290
<> 154:37f96f9d4de2 291 return result;
<> 154:37f96f9d4de2 292 }