STM32. Применение: STM32F107 + ST802RT1A + J00-0086NL = Ethernet. Часть 2. Раздел: STM32 Cortex M3.

Eugene's MCU

Воскресенье, 13.07.2014, 18:50

Главная | | Мой профиль | Выход | RSS
Меню сайта
Категории каталога
Рекламный блок





Рекомендовать этот сайт:

Главная » Статьи » » STM32 Cortex M3


STM32. Применение: STM32F107 + ST802RT1A + J00-0086NL = Ethernet. Часть 2

§
> Адаптация демонстрационного программного проекта
 
     В качестве базового примера программного проекта используется демонстрационный проект AN3102 от ST Microelectronics с использованием библиотеки стандартной периферии и драйвера Ethernet от ST и открытого стека TCP/IP lwIP, разработанного Adam Dunkels. Проект предназначен для запуска на отладочной плате STM3210C от STMicroelectronics и реализован без использования RTOS.
 
     Проект реализует следующие функции:
  • DHCP-клиент с выводом полученного IP-адреса на графический LCD.
  • Web-сервер с управлением четырьмя светодиодами отладочной платы и индикацией уровня сигнала на входе канала АЦП.
  • "Hello world” – приложение на базе telnet-сервера, отвечающее на введенный пользователем текст.
  • TFTP-сервер на базе SD-Card
  • Клиент-серверное приложение, позволяющее управлять светодиодами одной отладочной платы с помощью сенсорного экрана другой аналогичной платы.
     Для переноса проекта на наше устройство рассмотрим его отличия от платы STM3210C.
  
      1. Используется МК в 64-выводном корпусе, интерфейс RMII подключен без использования ремаппинга выводов.
      2. Используется микросхема PHY ST802RT1, вместо DP83848 – это ключевое отличие нашего устройства и ему будет уделено особое внимание.
      3. Используется три светодиода, подключенных к линиям PB0, PB1, PB5. Активный уровень – лог 0.
      4. Вывод МК ADC12_IN14 занят интерфейсом RMII, для демонстрации АЦП будем использовать свободный вывод ADC12_IN3.
      5. Отсутствует подключение SD-Card по SPI.
      6. Отсутствует графический LCD и сенсорный экран.
      7. Отсутствует внешний расширитель портов ввода-вывода (IO-Extender).

§
> Структура проекта
 
      Рассмотрим структуру проекта на примере версии для IAR EWARM v5. В состав проекта входят следующие группы исходного кода:
  
      - CMSIS – библиотека поддержки платформы Cortex M3.
      - efsl – библиотека поддержки файловой системы FAT и обмена с SD-Card по SPI.
      - ETHLib – библиотека драйвера контроллера Ethernet.
      - EWARMv5 – стартовый ассемблерный код от IAR.
      - FWLib – библиотека поддержки стандартной периферии STM32.
      - LwIP – стек протоколов TCP/IP (lwIP).
      - STM32_EVAL – библиотека поддержки периферии отладочной платы.
      - User – пользовательские приложения.

      Раскроем список файлов User и рассмотрим его более детально:
  
      - client.c – реализация клиентского приложения.
      - helloworld.c – реализация сервера Telnet.
      - httpd.c – реализация Web-сервера.
      - main.c – основной модуль программы.
      - netconf.c – выбор конфигурации клиент/сервер и IP-адреса.
      - server.c – реализация серверного приложения.
      - stm32f107.c – функции инициализации периферии МК.
      - stm32f107_it.c – пользовательские обработчики прерываний.
      - tftpserver.c – реализация TFTP-сервера.
      - tftputils.c – поддержка протокола TFTP.
 
      Далее начнем модификацию проекта по следующему плану:
  
      - Удаление неиспользуемых модулей.
      - Контрольная компиляция.
      - Корректировка функций поддержки периферии отладочной платы.
      - Корректировка функций инициализации периферии МК.
      - Корректировка функций инициализации PHY.
      - Настройка стека lwIP.
      - Компиляция и проверка на устройстве.

§
> Удаление неиспользуемых модулей
 
     Для упрощения задачи и по причине отсутсвия аппаратной поддержки, удалим из проекта следующие модули: TFTP-сервер (tftpserver.c, tftputils.c), клиент-серверное приложение (client.c, server.c), файловую систему (группа efsl), поддержку LCD (stm3210c_eval_lcd.c), поддержку расширителя ввода-вывода (stm3210c_eval_ioe.c). Из модуля stm32f107_it.c удаляем функцию обработчик прерывания от расширителя ввода-вывода void EXTI15_10_IRQHandler(void).
  
      Теперь нужно "заглушить” обращения к функциям графического LCD. Проще всего это сделать, подключив к проекту файл с набором пустых функций, совпадающих по именам с функциями из файла stm3210c_eval_lcd.c. В будущем, вывод на LCD можно будет перенаправить в UART или на символьный LCD (HD44780), написав соответствующие функции. 
  
     Файл patch_lcd.c   

     #include "stm3210c_eval_lcd.h"
  
     void LCD_DisplayStringLine(uint8_t Line, uint8_t *ptr) {}
     void LCD_SetTextColor(__IO uint16_t Color) {}
     void LCD_SetBackColor(__IO uint16_t Color) {}
     void LCD_DrawRect(uint8_t Xpos, uint16_t Ypos, uint8_t Height, uint16_t Width) {}
     void LCD_Clear(uint16_t Color) {}
      
 
      Далее найдем обращения к функциям инициализации модулей, удаленных из проекта. Из файла main.c необходимо удалить вызов tftpd_init(), из файла stm32f107.c – вызов STM3210C_LCD_Init(), из файла netconf.c – вызовы server_init(), IOE_Config(), IOE_ITConfig(IOE_ITSRC_TSC), client_init(). После этого необходимо скомпилировать проект, чтобы убедиться, что ошибок на стадиях компиляции и линковки в нем нет.

§
> Корректировка функций поддержки периферии отладочной платы
 
     На следующем этапе необходимо настроить библиотеку поддержки отладочной платы для корректной работы светодиодов, кнопок и USART. В нашем устройстве кнопки и светодиоды подключены к следующим линиям:
  
      LED1 – PB0
      LED2 – PB1
      LED3 – PB5
      KEY1 – PC0
      KEY3 – PC2
      KEY4 – PC3

        На плате STM3210C имеется также светодиод LED4, который в нашем устройстве виртуально объединяется с LED1. Также настроим COM-порт на USART1 (RXD1 – PA10, TXD1 – PA9). 
  
     Настройка производится модификацией файла stm3210c_eval.h :

      #define LEDn 4
      #define LED1_GPIO_PORT GPIOB
      #define LED1_GPIO_CLK RCC_APB2Periph_GPIOB
      #define LED1_GPIO_PIN GPIO_Pin_0

      #define LED2_GPIO_PORT GPIOB
      #define LED2_GPIO_CLK RCC_APB2Periph_GPIOB
      #define LED2_GPIO_PIN GPIO_Pin_1

      #define LED3_GPIO_PORT GPIOB
      #define LED3_GPIO_CLK RCC_APB2Periph_GPIOB
      #define LED3_GPIO_PIN GPIO_Pin_5

      #define LED4_GPIO_PORT GPIOB
      #define LED4_GPIO_CLK RCC_APB2Periph_GPIOB
      #define LED4_GPIO_PIN GPIO_Pin_0 //Совпадает с LED1

      #define BUTTONn 3 /*!< Joystick pins are connected to an IO Expander (accessible through I2C1 interface) */

      #define WAKEUP_BUTTON_PORT GPIOC
      #define WAKEUP_BUTTON_CLK RCC_APB2Periph_GPIOC
      #define WAKEUP_BUTTON_PIN GPIO_Pin_0
      #define WAKEUP_BUTTON_EXTI_LINE EXTI_Line0
      #define WAKEUP_BUTTON_PORT_SOURCE GPIO_PortSourceGPIOC
      #define WAKEUP_BUTTON_PIN_SOURCE GPIO_PinSource0
      #define WAKEUP_BUTTON_IRQn EXTI0_IRQn

      #define TAMPER_BUTTON_PORT GPIOC
      #define TAMPER_BUTTON_CLK RCC_APB2Periph_GPIOC
      #define TAMPER_BUTTON_PIN GPIO_Pin_2
      #define TAMPER_BUTTON_EXTI_LINE EXTI_Line2
      #define TAMPER_BUTTON_PORT_SOURCE GPIO_PortSourceGPIOC
      #define TAMPER_BUTTON_PIN_SOURCE GPIO_PinSource2
      #define TAMPER_BUTTON_IRQn EXTI2_IRQn

      #define KEY_BUTTON_PORT GPIOC
      #define KEY_BUTTON_CLK RCC_APB2Periph_GPIOC
      #define KEY_BUTTON_PIN GPIO_Pin_3
      #define KEY_BUTTON_EXTI_LINE EXTI_Line3
      #define KEY_BUTTON_PORT_SOURCE GPIO_PortSourceGPIOC
      #define KEY_BUTTON_PIN_SOURCE GPIO_PinSource3
      #define KEY_BUTTON_IRQn EXTI3_IRQn

      #define COMn 1

      #define EVAL_COM1 USART1
      #define EVAL_COM1_GPIO GPIOA
      #define EVAL_COM1_CLK RCC_APB2Periph_USART1
      #define EVAL_COM1_GPIO_CLK RCC_APB2Periph_GPIOA
      #define EVAL_COM1_RxPin GPIO_Pin_10
      #define EVAL_COM1_TxPin GPIO_Pin_9
    
 
     При рассмотрении отличий нашего устройства от платы STM3210C было отмечено, что светодиоды включаются уровнем логического нуля. 
 
     Для корректной работы необходимо исправить в файле stm32_eval.c функции:
      void STM_EVAL_LEDOn(Led_TypeDef Led)
      {
            // GPIO_PORT[Led]->BSRR = GPIO_PIN[Led];
            GPIO_PORT[Led]->BRR = GPIO_PIN[Led]; // Установка бита в 0
      }
      void STM_EVAL_LEDOff(Led_TypeDef Led)
      {
            //GPIO_PORT[Led]->BRR = GPIO_PIN[Led];
            GPIO_PORT[Led]->BSRR = GPIO_PIN[Led];  // Установка бита в 1 
      } 
 
     В инициализации USART необходимо исправить:
     #elif defined (USE_STM3210C_EVAL)
      if (COM == COM1)
      {
            /* Enable the USART2 Pins Software Remapping */
            //GPIO_PinRemapConfig(GPIO_Remap_USART2, ENABLE);
            //RCC_APB1PeriphClockCmd(COM_USART_CLK[COM], ENABLE);
            RCC_APB2PeriphClockCmd(COM_USART_CLK[COM], ENABLE); //USART1 на APB2!
      }
      #endif 
 

§
> Корректировка функций инициализации периферии МК
 
     Функции инициализации периферии МК размещены в файле stm32f107.c и вызываются через функцию System_Setup(). Здесь нужно исправить настройку на USART1.
 
 
      //* Enable USART2 clock */
      // RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2, ENABLE);
      RCC_APB1PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);
      Номер канала АЦП задается в функции ADC_Configuration(). Изменим его следующим образом:
      /* ADC1 regular channel14 configuration */
      // ADC_RegularChannelConfig(ADC1, ADC_Channel_14, 1, ADC_SampleTime_13Cycles5);
      ADC_RegularChannelConfig(ADC1, ADC_Channel_3, 1, ADC_SampleTime_13Cycles5);
  
 
     Функция GPIO_Configuration() задает режимы работы выводов МК, используемых для Ethernet и АЦП. Здесь следует обратить внимание на то, что RMII используется без ремаппинга, а порт GPIOD в нашем устройстве отсутствует вообще. В результате код будет выглядеть следующим образом:
  
 
void GPIO_Configuration(void)
{
      GPIO_InitTypeDef GPIO_InitStructure;

      /* ETHERNET pins configuration */
      /* AF Output Push Pull:
      - ETH_MII_MDIO / ETH_RMII_MDIO: PA2
      - ETH_MII_MDC / ETH_RMII_MDC: PC1
      - ETH_MII_TXD2: PC2 - НЕ ИСПОЛЬЗУЕТСЯ!
      - ETH_MII_TX_EN / ETH_RMII_TX_EN: PB11
      - ETH_MII_TXD0 / ETH_RMII_TXD0: PB12
      - ETH_MII_TXD1 / ETH_RMII_TXD1: PB13
      - ETH_MII_PPS_OUT / ETH_RMII_PPS_OUT: PB5 - НЕ ИСПОЛЬЗУЕТСЯ!
      - ETH_MII_TXD3: PB8 - НЕ ИСПОЛЬЗУЕТСЯ! */

      /* Configure PA2 as alternate function push-pull */
      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2;
      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
      GPIO_Init(GPIOA, &GPIO_InitStructure);

      /* Configure PC1, PC2 and PC3 as alternate function push-pull */
      // GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1 | GPIO_Pin_2;
      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
      GPIO_Init(GPIOC, &GPIO_InitStructure);

      /* Configure PB5, PB8, PB11, PB12 and PB13 as alternate function push-pull */
      //GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5 | GPIO_Pin_8 | GPIO_Pin_11 |
      // GPIO_Pin_12 | GPIO_Pin_13;
      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11 | GPIO_Pin_12 | GPIO_Pin_13;
      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
      GPIO_Init(GPIOB, &GPIO_InitStructure);

      /**************************************************************/
      /* For Remapped Ethernet pins */
      /*************************************************************/
      /* Input (Reset Value):
      - ETH_MII_CRS CRS: PA0 - НЕ ИСПОЛЬЗУЕТСЯ!
      - ETH_MII_RX_CLK / ETH_RMII_REF_CLK: PA1
      - ETH_MII_COL: PA3 - НЕ ИСПОЛЬЗУЕТСЯ!
      - ETH_MII_RX_DV / ETH_RMII_CRS_DV: PD8 -> PA7
      - ETH_MII_TX_CLK: PC3 - НЕ ИСПОЛЬЗУЕТСЯ!
      - ETH_MII_RXD0 / ETH_RMII_RXD0: PD9 -> PC4
      - ETH_MII_RXD1 / ETH_RMII_RXD1: PD10 -> PC5
      - ETH_MII_RXD2: PD11 - НЕ ИСПОЛЬЗУЕТСЯ!
      - ETH_MII_RXD3: PD12 - НЕ ИСПОЛЬЗУЕТСЯ!
      - ETH_MII_RX_ER: PB10 - НЕ ИСПОЛЬЗУЕТСЯ!
      - PHY_INT: PA6
      */

      /* ETHERNET pins remapp in STM3210C-EVAL board: RX_DV and RxD[3:0] */
      // GPIO_PinRemapConfig(GPIO_Remap_ETH, ENABLE); //Ремап не используется!

      /* Configure PA0, PA1 and PA3 as input */
      // GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_3;
      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1 | GPIO_Pin_6 | GPIO_Pin_7;
      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
      GPIO_Init(GPIOA, &GPIO_InitStructure);

      /* Configure PB10 as input */
      // GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
      // GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      // GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
      // GPIO_Init(GPIOB, &GPIO_InitStructure);
     
      /* Configure PC3 as input */
      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4 | GPIO_Pin_5;
      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
      GPIO_Init(GPIOC, &GPIO_InitStructure);

      /* Configure PD8, PD9, PD10, PD11 and PD12 as input */
      // GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8|GPIO_Pin_9|GPIO_Pin_10|GPIO_Pin_11|GPIO_Pin_12;
      // GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      // GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
      // GPIO_Init(GPIOD, &GPIO_InitStructure); /**/

      /* ADC Channel14 config --------------------------------------------------------*/
      /* Relative to STM3210D-EVAL Board */
      /* Configure PC.04 (ADC Channel14) as analog input -------------------------*/
      // PA3 - ADC1 CH03
      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3;
      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;
      GPIO_Init(GPIOA, &GPIO_InitStructure);

      /* MCO pin configuration------------------------------------------------- */
      /* Configure MCO (PA8) as alternate function push-pull */
      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
      GPIO_Init(GPIOA, &GPIO_InitStructure);
}
 

     Следующий шаг – инициализация Ethernet, производится в функции Ethernet_Configuration(). Необходимо проверить в начале файла stm32f107.c наличие строк:

 
      #define DP83848_PHY /* Ethernet pins mapped on STM3210C-EVAL Board */
      #define PHY_ADDRESS 0x01 /* Relative to STM3210C-EVAL Board */
      //#define MII_MODE /* MII mode for STM3210C-EVAL Board (MB784) (check jumpers setting) */
      #define RMII_MODE /* RMII mode for STM3210C-EVAL Board (MB784) (check jumpers setting) */
  
 
     Микросхема ST802RT1 по умолчанию имеет адрес на канале управления равный 1, этот адрес должен быть определен в константе PHY_ADDRESS. Определение RMII_MODE означает, что инициализацию Ethernet нужно производить для режима RMII, в том числе необходимо включить генерацию частоты 50МГц с помощью PLL3 на выход MCO.
  
     Инициализация Ethernet не требует корректировок, за исключением настройки PHY, о которой будет подробно рассказано в следующей части статьи.


При использовании материалов сайта ссылка на данный источник обязательна.

Категория: STM32 Cortex M3 | Добавил: EugenyAM (19.10.2011) | Автор:

Просмотров: 13114 | Комментарии: 5 | Рейтинг: 4.7/16 |
Всего комментариев: 5
0 Спам
* 1 Dmitry (18.12.2011 23:55) [Материал]
Интересная статья!
Не скоро выйдет 3 часть?

0 Спам
* 2 (28.12.2011 23:36) [Материал]
Да! тоже жду 3ю часть, скорее бы...

0 Спам
* 3 EugenyAM (29.12.2011 10:43) [Материал]
На каникулах выложим... сейчас конец года, работы много...

0 Спам
* 4 (06.01.2012 03:53) [Материал]
Очень интересно

0 Спам
* 5 Oleg_W (16.01.2012 18:20) [Материал]
Я понимаю, что работы очень много, да еще и праздники эти, но все же очень хочется увидеть поскорее продолжение :-[

Статистика

Наш магазин




Какую среду разработки Вы используете?

[ Результаты · Архив опросов ]
Всего ответов: 1556



Им нужна Ваша помощь: