Strana 1 z 1

UART - synchrónny a asynchrónny mód

Napísané: 18 Aug 2013, 20:31
od používateľa martin336
Tak po hodnej chvíľke otálania a hľadania na internete som sa rozhodol, že sa predsa len spýtam. Mám doma bluetooth module HC-06, ktorý komunikuje cez UART. Po naštudovaní toho, ako UART (USART) funguje, som prišiel k otázke, čo teda ten UART vlastne je. Pri synchrónnom móde mi to príde ako I2C, asynchrónny mód zase funguje o niečo/úplne inak. Ako mám teda nakonfigurovať svoje PIC-ko, aby som mohol cez UART komunikovať s tým bluetooth modulom?

Re: UART - synchrónny a asynchrónny mód

Napísané: 18 Aug 2013, 20:49
od používateľa jaromir
Synchronny mod je nieco medzi IIC a SPI - je tam jeden drot datovy a druhy je synchronizacny (clock)
K bluetooth modulu (tak ako aj na 99,9% ostatnych pouziti USART-u) potrebujes asynchronny rezim, kde na jendom dorte je prijem, na druhom vysielanie.

Vo svojich zdrojakoch pre 8-bitove PIC-ka pouzivam vacsinou toto nastavenie:
TXSTA = 0x24;
RCSTA = 0x90;
SPBRG = 51;
Pisem to z hlavy (uz to programujem nejaky ten piatok), nakonfiguruje to USART na asynchronny rezim, 9600 baud na taktovacej frekvencii 8MHz.
Najjednoduchsi scenar operacii okolo USART-u je takyto:
Pre vysielanie zapises do TXREG a cakas kym bit TRMT bude v nule. Pre citanie kontrolujes stav bitu RCIF a ak je jednotkovy, tak mozes citat z registra RCREG.
Da sa to urobit aj lepsie (zlozitejsie), trebars s vyuzitim preruseni, ale o tom inokedy.

Re: UART - synchrónny a asynchrónny mód

Napísané: 18 Aug 2013, 21:10
od používateľa boraicho
dik, ukladam si čo si napisal.

Re: UART - synchrónny a asynchrónny mód

Napísané: 18 Aug 2013, 21:31
od používateľa martin336
Diki

Re: UART - synchrónny a asynchrónny mód

Napísané: 18 Aug 2013, 22:34
od používateľa martin336
Práve pozerám jeden kód, ako jedno z riešení. "Receiving" majú v nekonečnej slučke, kde kontrolujú "reception". Premýšlam nad interruptom pri "príjme" a nad tým, ako to ovplyvní chod. A mám zopár otázok.

Môže mi riešenie cez interrupt prerušiť vysielanie/transmission? ... ako sa s tým potom človek vyrovná? Jednoducho keď sa to stane, tak to pošle znova? (neostane niečo vysieť len tak vo vzduchu? - čo na to prijímacie zariadenie? - neviem ako to má bluetooth protokol vyriešené)

Re: UART - synchrónny a asynchrónny mód

Napísané: 19 Aug 2013, 06:42
od používateľa jaromir
Ak raz zapises do TXREG-u, vysielanie bezi "same od seba" a akykolvek beh programu ho nemoze prerusit (okrem nasilneho vypnutia USART-u).

Re: UART - synchrónny a asynchrónny mód

Napísané: 02 Apr 2022, 10:31
od používateľa slonik
Pozdravujem.
Nechcel som zakladať novú tému tak som to dal sem. Som začiatočník v C takže nie všetko čo tu uvediem musí byť správne. Snažím sa tomu porozumieť, ale neviem prísť na problém, ktorý mám.
Chcem rozbehať komunikáciu usart. Teda rozbehal som ju ale nedokážem prijať reťazec znakov. Odosielanie znakov mi funguje bez problémov.

Používam prevodník CP2102.
na PIC16F887 mám zapojený displej SSD1306 cez SPI
používam MBLAB X IDE s kompilátorom XC8
cieľom je spojazdniť esp8266. Ešte som sa ale k esp nedostal pretože nedokážem prijať reťazec znakov.
Z PC odošlem napríklad "AHOJ" ale na displeji to nezobrazím, resp. zobrazím ale iba ako jeden znak, resp. nič alebo displej len preblikne.
procesor je taktovaný na 4MHz, baud 9600. Pri esp ho neskôr samozrejme zmením na 115200

inicializácia usart

Kód: Vybrať všetko

                   
void USARTinit (void)
{
 TRISC=0b11000000;//RX a TX nastavene ako vstupy RX=RC7, TX=RC6
     
 RCSTA=(1<<_RCSTA_SPEN_POSITION)  //povolenie USART
       |(1<<_RCSTA_CREN_POSITION);//povolenie prijmu
 
 TXSTA=(1<<_TXSTA_TXEN_POSITION)   //povolenie vysielaca
       |(1<<_TXSTA_BRGH_POSITION); //vysoka rychlost
 SPBRG=25;//9615  Bd
}
no a takto sa snažím prijať znaky a zobraziť ich na displej

Kód: Vybrať všetko


char* UARTcita()
{
  while(!RCIF);
  return RCREG;
}


char* prijem;

void main(void)
{
       if(PIR1bits.RCIF)
       {                      
           prijem = UARTcita();
            SSD1306_YX(2,2);
           lcdPrint(prijem);           
       }
}
dobre asi nie je keďže nič na displeji nezobrazim. Skúšal som už kadečo ale nič nefunguje. Nechcem už skúšať :-) ... rad by som pochopil prečo to nefunguje a ako by to malo byť aby mi to fungovalo
Ak sa nájde niekto kto používa PIC a je znalý problematike budem mu nesmierne vďačný.

Re: UART - synchrónny a asynchrónny mód

Napísané: 02 Apr 2022, 10:48
od používateľa mac26
Zobrazujes stale len jeden, posledny prijaty znak kdeze vsetko pises na jedno miesto na LCD. Takze sa ti zobrazi mozno tak J, ale skor nejaky nezmysel/nic, v zavislosti od nastavenia programu ktory pouzivas na odosielanie. Vacsinou sa na koniec totiz pridava koniec riadku (LF / CR+LF).

Jeden dalsi detail je, ze v zavislosti od dlzky vykonavania funkcii na vypis na ten LCD sa moze stat, ze nejaky znak proste preskocis pretoze si prave "nepocuval" na USART, ale obsluhoval LCD. Riesenim su prerusenia.

Re: UART - synchrónny a asynchrónny mód

Napísané: 02 Apr 2022, 10:55
od používateľa miso156
Overil by som si, kolko krat sa zavola funkcia UARTcita() pri prijme jedneho AHOJ.

Ak je to raz, tak je to OK.
Ak 4-krat, tak pri vypisovani si zakazdym prepises to iste miesto na displeji.

Mozes to zmerat osciloskopom ze do funkcii UARTcita() das togglovanie pinu.
Alebo si vytvoris premennu, inkrementujes ju pri kazdom zavolani funkcii UARTcita() a nakoniec si ju odosles cez UART ked ti uz odosielanie funguje. Alebo si ten pocet zobraz na Ledkach pripojenych na piny.

Taktiez by som si overil, ci ti spravne funguje vypisovanie na displej. Skus si len tak pre zaujimavost dat do char* prijem nejaky retazec. Ale to si uz pravdepodobne skusal.

Re: UART - synchrónny a asynchrónny mód

Napísané: 02 Apr 2022, 11:16
od používateľa slonik
mac26:
príznak prerušenia bude RCIF. v prerušení vopchám do premennej char*prijem dáta z RCREG a potom keď prerušenie skončí ich vypíšem na displej. Tak?

miso156:
keď dám do premennej char* prijem = "ahoj" displej mi ho vypíše bez problémov
vyskúšam skontrolovať počet vyvolania funkcie UARTcita()

presne toto mi robí chalani ako ste písali. Vypíše len posledný znak slova alebo nič.

bolo by ešte možné takéto riešenie?
vo funkcii UARTcita() prečítam z registra dáta a pomocou
for(int i=0;i<10;i++)
natisnem ich do
char pole [ i ] ;

a potom pomocou
char *strcpy(pole, prijem);

a ten prijem dám vytlačiť na displej


čo ste mi poradili vyskúšam samozrejme ..... som v práci takže sa dostanem k tomu až večer

Re: UART - synchrónny a asynchrónny mód

Napísané: 02 Apr 2022, 11:37
od používateľa miso156
Ja uz s MCU moc nerobim, tak ber s rezervou:

Cely retazec prijmes naraz tak, ze na koniec AHOJ pridas specialny znak \n a teda prijmas vo funkcii UARTcita() az kym sa tento znak neobjavi.

while(znak = RCREG != '\n') {

}


Mozno niekto poradi lepsi sposob.

Re: UART - synchrónny a asynchrónny mód

Napísané: 02 Apr 2022, 11:42
od používateľa maskrtnik01
Sú v zásade dve stratégie. Jedna ako opisujete, zvoliť si znak konca reťazca. Môže to byť všeličo, \r, \n, sekvencia \r\n, alebo aj \0.

Druhá možnosť, až tak sa nepoužíva, length prefixed. Najprv sa pošle dĺžka reťazca v binárnom tvare(8 16 alebo 32bit uint), potom sa pošle príslušný počet bajtov. Toto sa dá využiť aj na prenos binárnych dát.

Re: UART - synchrónny a asynchrónny mód

Napísané: 02 Apr 2022, 11:52
od používateľa slonik
ďakujem .... určite som sa pohol ďalej .... už len ten môj if v hlavnom programe je hlúposť ....
vyskúšam aj ten znak konca reťazca ....
ďakujem chalani za rady