aboutsummaryrefslogtreecommitdiffstats
path: root/os/hal
diff options
context:
space:
mode:
authorgdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4>2011-09-06 14:59:00 +0000
committergdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4>2011-09-06 14:59:00 +0000
commitb8ad6dbae6914316f731c99324ccb5052018dfbf (patch)
treedad92f08f90bda39f88d8126fa675ee883c1e7ae /os/hal
parentcd04106a830e70037225f9c7e312984a97447a3f (diff)
downloadChibiOS-b8ad6dbae6914316f731c99324ccb5052018dfbf.tar.gz
ChibiOS-b8ad6dbae6914316f731c99324ccb5052018dfbf.tar.bz2
ChibiOS-b8ad6dbae6914316f731c99324ccb5052018dfbf.zip
git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@3292 35acf78f-673a-0410-8e92-d51de3d6d3f4
Diffstat (limited to 'os/hal')
-rw-r--r--os/hal/include/mii.h1
-rw-r--r--os/hal/platforms/STM32/mac_lld.c68
2 files changed, 68 insertions, 1 deletions
diff --git a/os/hal/include/mii.h b/os/hal/include/mii.h
index 89ba69810..969f4a9d5 100644
--- a/os/hal/include/mii.h
+++ b/os/hal/include/mii.h
@@ -178,6 +178,7 @@
#define MII_DM9161_ID 0x0181b8a0
#define MII_AM79C875_ID 0x00225540
#define MII_KS8721_ID 0x00221610
+#define MII_STE101P_ID 0x00061C50
#endif /* _MII_H_ */
diff --git a/os/hal/platforms/STM32/mac_lld.c b/os/hal/platforms/STM32/mac_lld.c
index 37ca9e106..01a28a8b4 100644
--- a/os/hal/platforms/STM32/mac_lld.c
+++ b/os/hal/platforms/STM32/mac_lld.c
@@ -29,7 +29,7 @@
#include "ch.h"
#include "hal.h"
#include "mii.h"
-#
+
#if HAL_USE_MAC || defined(__DOXYGEN__)
/*===========================================================================*/
@@ -38,6 +38,20 @@
#define BUFFER_SLICE ((((MAC_BUFFERS_SIZE - 1) | 3) + 1) / 4)
+/* MII divider optimal value.*/
+#if (STM32_HCLK >= 60000000)
+#define MACMIIDR_CR ETH_MACMIIAR_CR_Div42
+#elif (STM32_HCLK >= 35000000)
+#define MACMIIDR_CR ETH_MACMIIAR_CR_Div26
+#elif (STM32_HCLK >= 20000000)
+#define MACMIIDR_CR ETH_MACMIIAR_CR_Div16
+#else
+#error "STM32_HCLK below minimum frequency for ETH operations (20MHz)"
+#endif
+
+/* PHY address.*/
+#define MACMIIDR_PA (32 << 11)
+
/*===========================================================================*/
/* Driver exported variables. */
/*===========================================================================*/
@@ -64,6 +78,55 @@ static uint32_t tb[MAC_TRANSMIT_BUFFERS * BUFFER_SLICE];
/* Driver local functions. */
/*===========================================================================*/
+/**
+ * @brief Writes a PHY register.
+ *
+ * @param[in] reg register number
+ * @param[in] value new register value
+ */
+static void mii_write_phy(uint16_t reg, uint16_t value) {
+ uint32_t miiar;
+
+ miiar = ETH->MACMIIAR | ETH_MACMIIAR_MW | ETH_MACMIIAR_MB;
+ miiar = (miiar & ~ETH_MACMIIAR_MR) | (reg << 6);
+ ETH->MACMIIDR = value;
+ ETH->MACMIIAR = miiar;
+ while ((ETH->MACMIIAR & ETH_MACMIIAR_MB) != 0)
+ ;
+}
+
+/**
+ * @brief Reads a PHY register.
+ *
+ * @param[in] reg register number
+ */
+static uint16_t mii_read_phy(uint16_t reg) {
+ uint32_t miiar;
+
+ miiar = ETH->MACMIIAR | ETH_MACMIIAR_MB;
+ miiar = (miiar & ~(ETH_MACMIIAR_MR | ETH_MACMIIAR_MW)) | (reg << 6);
+ ETH->MACMIIAR = miiar;
+ while ((ETH->MACMIIAR & ETH_MACMIIAR_MB) != 0)
+ ;
+ return (uint16_t)ETH->MACMIIDR;
+}
+
+/**
+ * @brief MII/RMII interface initialization.
+ */
+static void mii_init(void) {
+ uint32_t i;
+
+ for (i = 0; i < 31; i++) {
+ ETH->MACMIIDR = (i << 6) | MACMIIDR_CR;
+ if ((mii_read_phy(MII_PHYSID1) == (PHY_ID >> 16)) &&
+ (mii_read_phy(MII_PHYSID2) == (PHY_ID & 0xFFF0)))
+ return;
+ }
+ /* Wrong or defective board.*/
+ chSysHalt();
+}
+
/*===========================================================================*/
/* Driver interrupt handlers. */
/*===========================================================================*/
@@ -121,6 +184,9 @@ void mac_lld_start(MACDriver *macp) {
while (ETH->DMABMR & ETH_DMABMR_SR)
;
+ /* MII initialization.*/
+ mii_init();
+
/* Descriptor chains pointers.*/
ETH->DMARDLAR = (uint32_t)rd;
ETH->DMATDLAR = (uint32_t)rd;