Po předchozím dílu, nastala odmlka pro mou zaneprázdněnost. Ale nyní pokračujeme s ARM Cortex M4 a USB, použijeme kit jako Virtuální COM port, což je jeden z možných způsobů komunikace.


Úvod

Nejdřív proč jsem jako první zvolil Virtual COM port, tj. Communication Device Class (jak si doufám pamatujete z předchozích dílů). Zvolil jsem jej proto, že mnoho aplikací s MCU je propojeno s nějakým PC pomocí COM portu. A proto je pomocí této cesty možné nahradit starší mcu novějším, který ale nebude komunikovat přes COM port, ale přes USB, nicméně ovládací aplikace na PC bude stále fungovat stejně dobře jako dříve - bude jí připadat že stejně jako za stara komunikuje přes COM port, i když to ve skutečnosti nebude pravda.
Co budete k tomuhle dílu potřebovat? Stačí STM32F4 Discovery kit, USB kabel s Mini USB B konektorem na připojení kitu na napájení a k ladění přes ST-Link a pak budete potřebovat druhý USB kabel, s Micro A nebo Micro B USB konektorem na druhé straně (já použil kabel od Kindle čtečky, ale můžete podobný kabel koupit v Tescu za 49 Kč, cena mě příjemně překvapila).


Popis aplikace

Dumal jsem nad tím, jaký příklad zvolit, aby viditelně fungoval a přitom byl jednoduchý. Takže jsem došel k závěru, že aplikace bude na základě přijímaných znaků rozsvěcet modrou LED a když se stiskne USER tlačítko na kitu, tak po USB odešle do virtuálního sériového portu znak ("A"). Je to tedy jen školní demo aplikace, ve skutečnosti můžete odesílat naměřená data, nebo cokoliv jiného, program si snadno upravíte.
Úpravy programu - proboha, opravujte jen to, co je potřeba, pokud nevíte co dělají jiné části, tak do nich nešťourejte. Důvod je následující - STMicroelectronics stále vyvíjí USB knihovnu a mám pocit že ještě nedospěli k finální verzi. Tudíž ta knihovna kterou jsem použil (pochopitelně nejnovější) je jaksi dosti nepřehledná a na závěr psaní programu jsem strávil s laděním funkčnosti celé dva dny a to mám výhodu v tom, že jsem již pár USB aplikací realizoval a tuším která bije. Proto pokud jste začátečníci, tak buďte opatrní se změnami v kódu.


Realizace

Nejdříve zprovozněte vše na PC straně. Tj. stáhnete si nejnovější Virtual COM Driver od STMicroelectronics (viz odkazy na konci textu), rozbalte jej a nainstalujte! Pak si spusťte Atollic TrueSTUDIO v 2.2.0 (ve kterém jsem to psal a odladil, nebo nynější novou verzi 2.3.0 ve které to doufám také bude chodit) a naimportujete si projekt příkladu k tomuto dílu. A nyní se můžeme podívat na obsah projektu.

Soubory, které tvoří jádro projektu:
  • main.c
  • startup_stm32f4xx.s - raději pro sichr jej mám přímo zde
  • stm32f4xx_conf.h - nechávám všechny knihovnu odkomentované, přeloží se to jen jednou
  • stm32f4xx_it.c a stm32f4xx_it.h - obsluhy přerušení
  • stm32f4_discovery.c a stm32f4_discovery.h - knihovna k discovery, tlačítka a LED
  • system_stm32f4xx.c - základní konfigurace mcu, frekvence jádra, atd.
  • usbd_cdc_vcp.c a usbd_cdc_vcp.h - zde je podstatná část kódu týkajícího se realizace VCP
  • usbd_conf.h, usbd_desc.c a usbd_desc.h - konstanty descriptoru a popisovače
  • usbd_usr.c - uživatelská vrstva
  • usb_bsp.c - zde najdete inicializaci pinů pro USB komunikaci, atd.
  • usb_conf.h - drobnosti, jako nastavení velikosti bufferů pro endpointy, atd.



Jak je u USB aplikací běžné, hlavní main cykl je velmi jednoduchý:
/* zapneme LED3 */
  STM32F4_Discovery_LEDOn(LED3);   /* oranzova */
  Delay(0xFFFF);

  USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID,  &USR_desc, &USBD_CDC_cb, &USR_cb);

  __IO uint32_t i = 0;  

  while (1)
  {
    if (i++ == 0x100000)
    {
        STM32F4_Discovery_LEDToggle(LED4);  /* zelena */
        i = 0;
    }
  }
}


Takže na začátku, abychom věděli, že se něco děje, zapneme oranžovou LED a pak v hlavním cyklu blikáme zelenou LED. To bude fungovat vždy, i když nám USB nepojede. Vlastní aplikace funguje na základě přerušení. User tlačítko je namapováno na EXTI přerušení (pokud nevíte oč jde, tak si najděte příslušný díl seriálu k STM32 VL Discovery). Po stisku tlačítka se provede handler EXTI přerušení (naleznete v stm32f4xx_it.c), který volá DISCOVERY_EXTI_IRQHandler(), který se nachází v usbd_cdc_vcp.c, kde je taky většina obsluhy CDC_VCP zařízení. Aby jste měli situaci při předělávání programu jednodušší, tak jsem ponechal původní verzi funkční - takže příjem přes USART1 je přesměrován přes USB na virtuální COM port v PC a navíc vedle toho ještě provádí naše záměry. Proto vypadá obsluha přerušení takto:
void DISCOVERY_EXTI_IRQHandler(void)
{       VCP_DataTx (0, (uint32_t) 'A');
}


Tedy, odesíláme znak "A" do virtuálního COM portu - VCP.

Co se týče opačného směru, tak ten je zpracován funkcí VCP_DataRx, která vypadá následovně (zde jsem přesměrování na USART zakomentoval):
static uint16_t VCP_DataRx (uint8_t* Buf, uint32_t Len)
{
        uint32_t i;

        /* puvodni verze realizujici presmerovani USART portu na USB virtualni port */
        /*
        for (i = 0; i < Len; i++)
        {
                USART_SendData(DISCOVERY_COM, *(Buf + i) );
                while(USART_GetFlagStatus(DISCOVERY_COM, USART_FLAG_TXE) == RESET);
        }
        */


        /* ****************************************************************** */
        /* nova verze ktera rozsviti LED6 pokud prijde 'a' nebo 'A'
         * a zhasne led pokud prijde 's' nebo 'S' */

        for (i = 0; i < Len; i++)
        {
                if (*(Buf + i) == 'a' || *(Buf + i) == 'A' )
                {
                        STM32F4_Discovery_LEDOn(LED6);  /* modra */
                }
                else if (*(Buf + i) == 's' || *(Buf + i) == 'S' )
                {
                        STM32F4_Discovery_LEDOff(LED6);  /* modra */
                }
        }
        return USBD_OK;
}


Jak vidíte, není to žádná věda, pokud se nebudete hrabat ve zbytku kódu Ještě bych upozornil na soubor usbd_usr.c, který obsahuje uživatelskou aplikační vrstvu reagující na dění na USB portu. Takže tam mám napsáno třeba:
void USBD_USR_Init(void)
{  
  /* Initialize LEDs */
  STM32F4_Discovery_LEDInit(LED5); /* cervena */
}


čímž si připravím LED, abych s ním mohl blikat například v následující funkci:
void USBD_USR_DeviceConfigured (void)
{
        /* LCD_UsrLog("> VCP Interface configured.\n"); */
        STM32F4_Discovery_LEDOn(LED5); /* cervena */
}


Červenou LED rozsvítím, když je zařízení připojené a zkonfigurované po enumeraci (viz předcházející díl s popisem States USB spojení). Takže když si program přeložíte, nahrajete přes Dubug do kitu a spustíte (bez breikpointu zatím), tak po připojení druhého kabelu mezi kit a USB konektor na PC by se měly provést následující akce:
1. rozsvítí se červená LED na kitu,
2. na PC se vytvoří nový Virtuální sériový port (zkontrolujte v Ovládací Panely - System - Hardware - Správce zařízení a tam rozklikněte (Porty COM a LPT)
3. rozsvítí se další zelená LED těsně vedle konektoru (indikuje přítomnost VUSB)

Nyní můžete pustit na PC Hyperterminál a připojit jej na to číslo COM portu, které uvidíte ve Správci Zařízení. Parametry 115200, 8 bit, No parity, HW řízení. A pak přijde ověření funkčnosti. Když stisknete A nebo a na klávesnici (a okno Hyperterminálu je aktivní), tak se na kitu rozsvítí modrá LED. Naopka když stisknete S nebo s, tak zhasne. A když stisknete na kitu USER tlačítko (modré), tak se na Hyperteminálu zobrazí znak A.


Závěr

Nikde na internetu jsem nenašel že by někdo publikoval informaci o tom že dokázal zprovoznit VCP na STM32F4 Discovery kitu, tudíž to asi není taková brnkačka jak jsem si na začátku myslel a také jsem to musel rychtovat několik dní. Tudíž čest a sláva, aspoň ve Virtual COM port na Cortex M4 jsme na světě první
Všiml jsem si že kolega v diskuzi přiznal, že rozběhal na kitu nějakou jinou variantu USB komunikace, tak jsem zvědav zda jí pošle k publikování. Pokud ne, tak mám v plánu nějakou další variantu napsat ale s drobným časovým odstupem. Doufám že publikovaný projekt Vám umožní snadněji proniknout do tajů USB komunikace, a že se brzy pochlubíte nějakými konstrukcemi využívající USB komunikace. Hezkou konstrukcí by třeba mohl být USB Grafický displej využívající LCD monitor s běžným DSUB konektorem - kit má na to dost paměti i rychlosti Pokud to někdo napíše, tak dostane nejméně dva STM32 mcu!

Pokud se domníváte, že si text a přiložený demoprogram zaslouží Vaše ocenění, tak můžete poslat svou dotaci. Předem děkuji všem! Podpoříte tím vznik dalších článků.





Odkazy

Materiál k HID naleznete odkaz
Materiál k CDC naleznete odkaz

Projekt k tomuto dílu je zde.

Vitual COM Driver na webu STMicroelectronics naleznete drive zde a nyní drive zde.

Začínáme s STM32F4 kitem 1. odkaz (vývojové prostředí, atd.)
Začínáme s STM32F4 kitem 2. odkaz (USB Úvod)
Začínáme s STM32F4 kitem 3. odkaz (USB Enumerace)