forum.mcontrollers.com - hlavní stránka forum.mcontrollers.com - fórum

 

.: fórum - hlavní stránka :.
Technology Stronghold by Rudolf Vesely
How to build Microsoft System Center hosted cloud series
FAQFAQ HledatHledat Seznam uživatelůSeznam uživatelů Uživatelské skupinyUživatelské skupiny RegistraceRegistrace
ProfilProfil StatistikaStatistika Soukromé zprávySoukromé zprávy PřihlášeníPřihlášení

 
softwarový sér. port u AT89C51ED2

 
Přidat nové téma   Zaslat odpověď    Obsah fóra mcontrollers.com -> 8051 / 8052
 
Anonymní






PříspěvekZaslal: 09 duben 2009, 23:32    Předmět: softwarový sér. port u AT89C51ED2 Citovat

Ahoj,poradil by mě někdo jak si udělat na 51 softwarový sér port? Už jsem něco našel na http://www.atmel.com/dyn/resources/prod_documents/doc3ab877f2ec329.pdf ale moc tomu nerozumím a nejradši bych to chtěl napsat v Céčku.
Návrat nahoru
 

 
Chuck
Častý přispěvatel
Častý přispěvatel


Založen: 31.3.2009
Příspěvky: 31
Bydliště: OV

PříspěvekZaslal: 10 duben 2009, 0:37    Předmět: Citovat

Eat this!

http://www.best-microcontroller-projects.com/pic-serial-port.html
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Anonymní






PříspěvekZaslal: 10 duben 2009, 8:43    Předmět: Citovat

koukám sice že je to na pic, ale ta teorie je na 51 určitě stejná. Koukal jsem na ten program:
kód:

void _Soft_USART_Write(unsigned short chr) {                     
unsigned short mask=1,i;                                         
unsigned int data;                                               
                                                                 
   data = chr << 1;                                             
   data &= ~0x0001; // START bit (=0).                           
                                                                 
   // 10 output bits                                             
   for (i=0;i<9;i++) { // lsb 1st  8 bits                       
      if (mask & data) {                                         
         asm {CLRW}                                             
         SU_set; // output low for logic 1                       
      } else {                                                   
         SU_res;// output high for logic 0                       
         asm {CLRW}                                             
      }                                                         
      mask <<=1;                                                 
      delay_us(395); // 2400 simulate to calibrate the loop.     
   }

   SU_set; // stop bit
   delay_us(417); // 2400
}

a myslím si že ho celkem chápu. Prostě vezmu data a masku a navzájem to 8x rotuju a pak posílám 1 nebo 0,ale není mě jasné co dělá to
kód:
 asm{CLRW}

a
kód:
delay_us(395);

myslím že jedno bude ještě něco s tím odesláním na port a druhé nastavení rychlosti přenosu???
Návrat nahoru
 

 
Chuck
Častý přispěvatel
Častý přispěvatel


Založen: 31.3.2009
Příspěvky: 31
Bydliště: OV

PříspěvekZaslal: 10 duben 2009, 9:06    Předmět: Citovat

Omg. Kdyby to nemelo byt stejny proc bych Ti to posilal? CLRW je instrukce nulovani watchdogu myslim. A Delay Ti asi dava zpozdeni nebo delku jednoho bitu v seriovem prenosu. Jeho delkou nastavis baudrate.
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
jouda
Anonymní





PříspěvekZaslal: 17 duben 2009, 6:22    Předmět: Citovat

Ten reset watchdogu bych z funkce vyhodil, nulovat po kazdym odeslanym bitu je docela neefektivni, resetoval bych ho nekde pred volanim funkce...
Návrat nahoru
 

 
teo
Nováček
Nováček


Založen: 9.4.2009
Příspěvky: 7

PříspěvekZaslal: 17 duben 2009, 9:37    Předmět: Citovat

já to naprogramoval takhle, ale zatím netuším jestli to vůbec bude fungovat. Potřeboval jsem komunikaci oběma směry.
kód:

/* ========================================================================== */
/*                 ser data cteni                                             */
/* ========================================================================== */
ser_data_cteni:
maska2=0x01;      // 0000 0001
P3|=0x00;
if(P3==0x40)
        {
        cteni=1;
}
if(cteni==1)
      {
      cekej(1,5bitu)      //cekej 1,5 bitu
      for(ii=0;ii<8;ii++)
            {
            if(P3==0x40)
                  {
                  data_in |= maska2;
                  cekej(1bit);   // 1bit
                  }
            else
                {
                 data_in &=0xff;   
                }
              }
              maska2 << 1;
      cteni=0;
      cekej(0,5bitu)
}
/* ========================================================================== */
/*                 ser data zapis                                             */
/* ========================================================================== */
ser_data_zapis:                                                         
int data_out;
int maska=0x80;
int ii;                                                                                           
P3&=0xDF; // START bit =0                         
cekej(1bit);        //cekej 1bit                                                                                                           
for (ii=0;ii<9;ii++)
                {                     
                if (maska & data_out)
                                {                                                                                   
                                P3|=0x20; // vystup log 1                       
                                }
                else
                    {                                                   
                    P3&=0xDF;   // vystup log 0                                                                 
                    }                                                         
                data_out = data_out << 1;                                                 
                cekej(1bit); //cekej 1bit
                }
P3|=0x20; // vystup log 1 -> stop bit = 1
cekej(1bit); //cekej 1bit

s tím že fce cekej(cislo) je dána přesně přerušením od čítače/časovače a zbejvá nastavit na nejmenší krok a pak přesně dopočítat časy aby to komunikovalo 38400 bit/s.
P.S.: to nahoře anonimní je můj dotaz Wink
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Martin
ATmega pouzivatel
ATmega pouzivatel


Založen: 5.1.2008
Příspěvky: 1495

PříspěvekZaslal: 17 duben 2009, 11:37    Předmět: Citovat

Zdravim,

nechcem moc cerit tiche vody typu "delay_us", ale prave taketo riesenia
dehonestuju vybavu hw periferii jednocipakov.

Myslim, ze vacsinou sa od procesora ocakava, ze ak komunikuje, to automaticky neznamena, ze nema robit nic ineho (AD prevody, filtracia signalu, zobrazovanie na LCD, interakcia s tlacitkami, vypocty regulacnych sluciek, atd, atd). Obzvlast, ak caka na prijem nejakej spravy.

SW uart moze byt napisany tak ako bolo uvedene vyssie, ale ak je to mozne, za systemovejsie riesenie povazujem vyuzit HW vybavu procesora.
Konkretne na x51 (ale aj na ine typy) je dobre pouzit interupt od casovaca.
Predpokladam, ze MCU najprv caka na nejaku spravu od PC a potom na nu odpoveda, komunikacia typu 8N1.

Prijem:
Vstupny pin casovaca T vyuzijem na RX. 8b casovac nastavim do modu pocitania vstupnych impulzov a do pocitadla mu vlozim hodnotu 0xff. Prichodom dobeznej hrany na pine casovac pretecie a vyhodi prerusenie. Nie je teda potrebne obetovat na RX nejaky iny pin s funkciou INT.
V tomto preruseni zmenim mod citaca/casovaca na casovac a prednastavim cas na 1/2 Bd rychlosti. Samozrejme s prerusenim.
Po druhom preruseni otestujem, ci je vstupny signal v log.0. Ak ano, udalost prehlasim za platny start bit. Do predvolby nastavim cas 1 Bd rychlosti.
Postupne pride 8 preruseni. V kazdom z nich otestujem hodnotu pinu procesora (vstup pre T) a ulozim do nejakeho bajtu ako platne bity.
Pockam na deviate prerusenie. Ak je hodnota pinu 1, jedna sa o platny stop bit, prijaty bajt mozem ulozit do komunikacneho bufera - akoby mi prislo prerusenie od UARTu a celu cinnost opakujem.


Vysielanie:
Ten isty citac / casovac, ktory som pouzival pri prijme vyuzijem na odpocet vyslania bajtu. Predpokladam komunikaciu typu poloduplex.
Ak komunikujem cez budic RS485, prepnem smer na vysielanie (iny pin ako RX a TX.)
Pin procesora (iny ako som pouzil na RX, ale v zasade lubovolny) nastavim na log.0 (start bit), do predvolby vlozim cas 1 Bd rychlosti. Postupne pride 8 preruseni. V kazdom z nich nastavim na vystup prislusny bit z vysielaneho bajtu. Po deviatom preruseni nastavim pin na log.1 - stop bit. Ak komunikujem cez RS 232, cinnost ukoncim/pokracujem v odvysielani dalsieho bajtu, ak cez RS485, pockam na desiate prerusenie a otocim smer budica RS485 na prijem, ak uz nie je potrebne odvysielat dalsi bajt.


Ak komunikujem rychlostou 38400/9600Bd, potom cas medzi jednotlivymi bitmy je cca 26/104us.Osobne robim s ATmega (14.7456MHz) a tie za tu dobu urobia 383/1533 instrukcii. A to je naozaj dost dlha doba, aby sa procesor len tak flakal v nejakej zapraskanej casovej slucke. Okrem toho C prekladac program optimalizuje a bezduche casove slucky (ak nie su asm volatile) optimalizuje, pripadne cele vyhadzuje. s tym maju hlavne zaciatocnici psychicke problemy typu - ved som to tam napisal, tak preco to ten "blby" prekladac vyhadzuje a upravuje. No preto, lebo to nie je ASM a od prekladaca primarne chceme, aby nase programatorske "blaboly" optimalizoval do hustejsieho a rychlejsieho kodu. A pri rozne zapnutych optimalizaciach budu prirodzene casove/velkostne vysledky rozne.
Preto celkovo v C doporucujem sa funkciam typu delay_ms/us vyhybat (aj ked principialne sa pouzit daju, akurat brzdia cely procesor) a naucit sa vyuzivat ine prostriedky, ktore su na casove funkcie v jednocipoch urcene.

Horeuvedeny postup je uplne nezavisly, ci programujem v ASM, alebo v C.
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
teo
Nováček
Nováček


Založen: 9.4.2009
Příspěvky: 7

PříspěvekZaslal: 17 duben 2009, 14:23    Předmět: Citovat

Takže abych vše upřesnil. Zapojení vypadá takto:

mám tam připojený krystal 12MHz. Ale popravdě moc nevím jak to zapracovat do toho čítače časovače.Něco jsem napsal,ale jestli je to ok to nevím,zkusím to vyzkoušet.
kód:

/* ========================================================================== */
/*                 ser data cteni                                             */
/* ========================================================================== */
void cteni ()
{
mikros=0;
while(mikros==39){               //dokud neubehne 1,5 bitu vrat (39 mikrosekund)
                  //_nop_();     // nic nedelej
                  }   
for(ii=0;ii<8;ii++)
            {
            mikros=0;
            if(P3==0x40)
                  {
                  data_in |= maska2;
                  }
            else
                {
                 data_in &=0xff;   
                }
            while(mikros==26){               //dokud neubehne 1 bit vrat (26 mikrosekund)
                                //_nop_();
                                }
            maska2 << 1;
            }             
while(mikros==13){               //dokud neubehne 0,5 bitu vrat (13 mikrosekund)
                  //_nop_();     // nic nedelej
                  }
}
/* ========================================================================== */
/*                 ser data zapis                                             */
/* ========================================================================== */
void zapis ()
{                                                         
maska=0x80;                                                                                         
P3&=0xDF; // START bit =0 
mikros=0;                       
while(mikros==26){               //dokud neubehne 1 bit vrat (26 mikrosekund)
                  //_nop_();     // nic nedelej
                  }                                                                                                         
for (ii=0;ii<9;ii++)
                {                     
                if (maska & data_out)
                                {                                                                                   
                                P3|=0x20; // vystup log 1                       
                                }
                else
                    {                                                   
                    P3&=0xDF;   // vystup log 0                                                                 
                    }                                                         
                data_out = data_out << 1;                                                 
                while(mikros==26){               //dokud neubehne 1 bit vrat (26 mikrosekund)
                  //_nop_();     // nic nedelej
                  }
                mikros=0;   
                }
P3|=0x20; // vystup log 1 -> stop bit = 1
while(mikros==26){               //dokud neubehne 1 bit vrat (26 mikrosekund)
                  //_nop_();     // nic nedelej
                  } 
}
/* ========================================================================== */
/*                 funkce preruseni                                           */
/* ========================================================================== */
void timer0(void) interrupt 1
{
static int i;
if(i<1000){           //casova smycka 1ms
          i++;
        }
else
    {
    ms++;
    i=0;
    }
    mikros++;           // pocita mikro sekundy >> jeden krok citace/casovace 
ser_data_cteni:
maska2=0x01;      // 0000 0001
P3|=0x00;
if(P3==0x40)
        {
        cteni();
}
ser_data_zapis:
if(data_out!=0){
                  zapis();
                  }
return;
}

/* ========================================================================== */
/*                 HLAVNI FUNKCE                                              */
/* ========================================================================== */
void main()
{
/* ========================================================================== */
/*                 nastaveni citace                                           */
/* ========================================================================== */

TMOD = 0x02;
TH0 = 256-1;
TR0 = 1;
ET0 = 1;
EA = 1;

while(1)
{


}


Arrow administrator: příspěvek byl upraven
Externí soubor byl uploadnut na server.



UART.jpg
 Komentář:
 Velikost:  32.86 kB
 Zobrazeno:  9608 krát

UART.jpg


Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Martin
ATmega pouzivatel
ATmega pouzivatel


Založen: 5.1.2008
Příspěvky: 1495

PříspěvekZaslal: 17 duben 2009, 16:00    Předmět: Citovat

Asi ani neskusaj Smile
Pod prerusenim mas zase nejake casove slucky, ktore Ti este moze prekladac zoptimalizovat a pripadne aj z programu vyhodit (dovody som pisal vyssie).

Okrem toho, ako vidim na RX do MCU (teda TX zo Zigbee modulu) mas privedeny /wr a nie vstup od citaca casovaca.
Musis si byt 110% isty, co oznacenie TX a RX na Zigbee znamena. Normalne by to malo znamenat, ze do RX na module ide signal TX z MCU a signal z TX na module ma ist do RX na MCU.

Nerobim s x51, tak ti neviem napisat program s presnym oznacenim registorom v Tvojom MCU, ale princip je rovnaky.

1) TX z modulu pripoj napr na vstup T0.
potom si prepis nasledovny algoritmus. Je to pre ATmega. Netestujem extra start bit, preto je tam na zaciatku 1.5 nasobok Bd

SIGNAL (COM5_SIG_TEST_START_BITU) - funkcia, ktora sa zavola po preteceni casovaca, ked je nastaveny v mode pocitadla vst impulzov a ma nastavenu predvolbu na 0xff

toto su vsetko makra, ktore si musis ty napisat podla svojho, ich vyznam je jasny z nazvov
COM5_ZAKAZ_PRERUSENIA_OVERFLOW_TIMER;
COM5_SET_TIMER_RX_TX_BIT; // zapni prijem od compare match
COM5_POVOLENIE_PRERUSENIA_COMAPRE_MATCH;

SIGNAL (COM5_SIG_TIMER_RX_TX_BIT) - funkcia, ktora sa zavola, ked pride prerusenie od compare match

kód:


// Definicia LOCALnych funkcii

// identifikacia start bitu, prisla dobezna hrana signalu
SIGNAL (COM5_SIG_TEST_START_BITU)
{
   // nastav hodnotu compare match na 1.5 nasobok bitovej rychlosti a prerusenie od compare match
   SET(sw_status,ROZPRACOVANY_PRIJEM);
   COM5_PRAC_POCITADLO = 0x00;// prednastavenie hodnoty TCNT tak, aby pri najblizsiemu compare match doslo k preruseniu
   COM5_COMPAR_REGISTER = sw_predvolba_pre_1_5nasobok_bitu;
   sw_udr_prac = 0;
   sw_pocitadlo_bitov = 0;
   COM5_ZAKAZ_PRERUSENIA_OVERFLOW_TIMER;
   COM5_SET_TIMER_RX_TX_BIT;  // zapni prijem od compare match
   COM5_POVOLENIE_PRERUSENIA_COMAPRE_MATCH;

   return;
}


SIGNAL (COM5_SIG_TIMER_RX_TX_BIT)
{
   uint8_t prac;
   
   COM5_COMPAR_REGISTER = sw_predvolba_pre_1nasobok_bitu;


   sw_pocitadlo_bitov++;

   // bezi prijem
   if TST(sw_status,ROZPRACOVANY_PRIJEM) {

      // test stop bitu
      if (sw_pocitadlo_bitov > 8) {
         if (GET_RX5) {
            sw_udr = sw_udr_prac;

// ****************** zrusenie prerusenia po prijati bajtu ****************
            RES(sw_status,ROZPRACOVANY_PRIJEM);
            COM5_ZAKAZ_PRERUSENIA_COMAPRE_MATCH;
            COM5_PRAC_POCITADLO = COM5_MAX_HODNOTA_PRAC_POCITADLA;// prednastavenie hodnoty TCNT tak, aby pri najblizsej dobeznej hrane prislo k preruseniu      
            COM5_SET_TEST_START_BITU;  // zapni prijem
            COM5_RES_INT_FLAG;
            COM5_POVOLENIE_PRERUSENIA_OVERFLOW_TIMER;
            POVOLENIE_PRERUSENIA;
// ************************************************************************

            // inicializacia funkcie PAUSE, lebo bolo nieco prijate
            timer_com5.timer = COM5_TIMEOUT_RX;
            prg_tb_timer(TB_5ms, TIMER_INIT, (TIMER_STRUCT * ) &timer_com5);

#if (COM5_ECHO == TRUE)

            sprava_prijata = TRUE;   
            mem[cnt_mem_max] = sw_udr;
            if (cnt_mem_max < (MAX_MEM - 1)) {
               cnt_mem_max++;
            }

            RES(sw_status,ROZPRACOVANY_PRIJEM);
            RES(sw_status,ROZPRACOVANE_VYSIELANIE);
            COM5_ZAKAZ_PRERUSENIA_COMAPRE_MATCH;
            COM5_PRAC_POCITADLO = COM5_MAX_HODNOTA_PRAC_POCITADLA;// prednastavenie hodnoty TCNT tak, aby pri najblizsej dobeznej hrane prislo k preruseniu      
            COM5_SET_TEST_START_BITU;  // zapni prijem
            COM5_POVOLENIE_PRERUSENIA_OVERFLOW_TIMER;
            return;
            
            // priprav nacitanie dalsieho bajtu
#else
            com5_struct.pracovny_bajt = sw_udr;
            prac = prg_prijaty_bajt((COM_STRUCT *)&com5_struct);

            if (prac == COM_VYPNI_PRIJEM) {

            // ak bol pri novej sprave este stale zablokovany box, iniciuj ho
               SET(com5_struct.status,SPRACUJ_PROTOKOL);
               RES(sw_status,ROZPRACOVANY_PRIJEM);
               COM5_ZAKAZ_PRERUSENIA_COMAPRE_MATCH;
               return;
            }
            RES(sw_status,ROZPRACOVANY_PRIJEM);
            RES(sw_status,ROZPRACOVANE_VYSIELANIE);
            COM5_ZAKAZ_PRERUSENIA_COMAPRE_MATCH;
            COM5_PRAC_POCITADLO = COM5_MAX_HODNOTA_PRAC_POCITADLA;// prednastavenie hodnoty TCNT tak, aby pri najblizsej dobeznej hrane prislo k preruseniu      
            COM5_SET_TEST_START_BITU;  // zapni prijem
            COM5_POVOLENIE_PRERUSENIA_OVERFLOW_TIMER;
            return;
#endif      
         }
         // nebol stop bit
         else prg_com5(COM_ZAPNI_PRIJEM, 0);
      }
      else {
         sw_udr_prac >>= 1; // rotacia do prava
         if (GET_RX5) {
            sw_udr_prac |= 0x80;
         }
         // skratenie casu testu stop bitu
         if (sw_pocitadlo_bitov == 8) COM5_COMPAR_REGISTER = sw_predvolba_pre_0_8nasobok_bitu;

      }
      return;
   }

   if TST(sw_status,ROZPRACOVANE_VYSIELANIE) {
      // generovanie start bitu

      if (sw_pocitadlo_bitov == 1) {
#if (COM5_ECHO == TRUE)

         if (cnt_mem == cnt_mem_max) { // ukonci vysielanie
            prg_com5(COM_ZAPNI_PRIJEM, 0);
            return;
         }
         else {
            if (cnt_mem == 0) sw_udr = 's';
            else sw_udr = mem[cnt_mem];

            if (cnt_mem < cnt_mem_max) cnt_mem++;
         }
#else         
         sw_udr = prg_vyslany_bajt((COM_STRUCT *)&com5_struct);
#endif
         if TST(com5_struct.setup,PREPINAJ_SMER) { // je rezim RS485
            COM5_SMER_RS485_RX;
         }

         RES_TX5;
      }
      else {
         if (sw_pocitadlo_bitov < 10) {
            if (sw_udr & 0x01) SET_TX5;
            else RES_TX5;
            sw_udr >>= 1;
         }
            // generuj 3x stop bit
         if (sw_pocitadlo_bitov == 10) {
            SET_TX5;
         }
         // otestuj, ci treba este vysielat
         if (sw_pocitadlo_bitov == 13) {
            if TST(com5_struct.setup,PREPINAJ_SMER) { // je rezim RS485
               COM5_SMER_RS485_RX;
            }
            sw_pocitadlo_bitov = 0;
#if (!(COM5_ECHO == TRUE))
            // ak sa uz nema nic odvysielat, potom prepni UART na prijem
            if (!(TST(com5_struct.status,JE_VYSIELANIE))) {
               prg_com5(COM_ZAPNI_PRIJEM, 0);
            }
#endif
         }
      }
      
      return;
   }
}



Ale z toho asi velmi mudry nebudes Smile, to bolo iba na ukazku ako fragment z realnej sw komunikacnej rutiny. Nie je tam uplne vsetko a o tom kode ani nemusime polemizovat. Uviedol som to iba ako dokaz, ze viem o com pisem.

Takze este raz mnemotechnicky. Neviem, ci ma x51 compare match, budem teda pisat algoritmus ako by bolo prerusenie iba od pretecenia casovaca. Predpokladam, ze sprava je ukoncena znakom 0x0d

kód:


#define FALSE 0x00
#define TRUE 0xff
#define KONCOVY_ZNAK 0x0d
#define MAX_POCET_BAJTOV 100

uint8_t prijaty_bajt, cnt_pom, bufer[MAX_POCET_BAJTOV], aktual_index, sprava_ukoncena = FALSE;

int main(void)
{
  fn_inicializacia_prijmu_bajtu();
  aktual_index = 0;
  // hlavna slucka, tusi rob co chces
  while(1) {

    if (sprava_ukoncena == TRUE) {
      fn_spracuj_protokol();
    }
    // ak neprisla sprava, kludne si volaj do kolecka svoje dalsie funkcie, napr na spracovanie displaya a tak podobne. Len sa cas od casu pozri, ci uz nahodou nebola prijata cela sprava.
  }
}


void fn_prerusenie_od_pretecenia(void)
{
  // ak bola sprava ukoncena a je zle osetrene vypnutie prerusenia, tak z funkcie hned vyskoc
  if (sprava_ukoncena == TRUE) return;


  // normalna cinnost rutiny
  if (cnt_pom == 0) {
      - nastav T0 ako casovac
      - nastav do T0 predvolbu tak, aby sa po uplynuti casu 0.5Bd vyvolalo prerusenie
  }
  // ak cakas start bit
  if (cnt_pom == 1)  {
    //  a na pine T0 je naozaj nula, potom pokracuj
    if (!(PORT_P3 & (1<<pin_T0))) {
      - nastav do T0 predvolbu tak, aby sa po uplynuti casu 1 Bd vyvolalo prerusenie
    }
    // nejednalo sa o start bit, ale asi o nejaky sum
    else {
       fn_inicializacia_prijmu_bajtu();
       return;
    }
 }
 if (cnt_pom > 1) && (cnt_pom <= 9) {
    prijaty_bajt = prijaty_bajt<<1;
    if (PORT_P3 & (1<<pin_T0))) {
      prijaty_bajt = prijaty_bajt + 0x01;
 }
 // otestuj stop bit
 if (cnt_pom == 10) {
    if (PORT_P3 & (1<<pin_T0))) {
        bufer[aktual_index] = prijaty_bajt;
        if (prijaty_bajt !=KONCOVY_ZNAK) {
           aktual_index++;
           // ochrana proti preteceniu bufera
           if (aktual_index >=MAX_POCET_BAJTOV)  aktual_index = 0;
       }
       else {
           // v premennej aktual_index mas pocet priajtych bajtov
           sprava_ukoncena = TRUE;
           - zakaz prerusenia od T0
           return;
       }
    }
    // neprisiel stop bit
    else {
       fn_inicializacia_prijmu_bajtu();
       return;
    }
  }
  cnt_pom++;
}

void  fn_inicializacia_prijmu_bajtu(void)
{
        - nastav pin T0 ako vstupny
        - nastav do predvolby T0 0xff
        - nastav prerusenie od pretecenia T0
        prijaty_bajt = 0;
        cnt_pom = 0;
}

void  fn_spracuj_protokol(void)
{

  // co len chces
  // ....
  // koniec co len chces

  sprava_ukoncena = FALSE;
  fn_inicializacia_prijmu_bajtu();
  aktual_index = 0;
}




Dufam, ze som v druhom kode nenarobil nejake principialne chyby, treba to skontrolovat. Hlavne si vsimni, ze nikde ziadne cakacie slucky Smile
Obdobne naprogramujes i vysielanie. Na zaciatok prerusovacej rutiny si este hodis podmienku ci sa sprava prijima, alebo vysiela. Pri vysielani vyuzivas iba prerusenie od casovaca v periode casu 1Bd.
Prajem vela uspechov a daj vediet ze co a ako.
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
teo
Nováček
Nováček


Založen: 9.4.2009
Příspěvky: 7

PříspěvekZaslal: 20 duben 2009, 12:58    Předmět: Citovat

Moc pěkný postup, děkuji. Ale já myslel že bych tyto výstupy využíval normálně jako např bránu P2. a k tomu používal normální 8 bit čítač/čas co udělá vnitřní přerušení.Popravdě vůbec nevím jak udělat přerušení na T0.
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
teo
Nováček
Nováček


Založen: 9.4.2009
Příspěvky: 7

PříspěvekZaslal: 22 duben 2009, 20:27    Předmět: Citovat

poradil by mě někdo jak nastavit 16 bit čitač/časovač?aby např. každých 150 mikrosekund vytvořil přerušení.Krystal je 12MHz.
mám nastavený 8bit takto a funguje super, takže bych potřeboval podle stejného postupu i ten druhý,ale nějak se v návodu strácím:
kód:

void timer0(void) interrupt 1
{
zde je obsluha preruseni
}
void main()
{
TMOD = 0x02;
TH0 = 256-100;
TR0 = 1;
ET0 = 1;
EA = 1;
}
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Martin
ATmega pouzivatel
ATmega pouzivatel


Založen: 5.1.2008
Příspěvky: 1495

PříspěvekZaslal: 24 duben 2009, 0:32    Předmět: Citovat

V tom Ti neporadim - robim s inym mcu. Na to su tu povolanejsi Smile
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Divous
Profesionál
Profesionál


Založen: 24.4.2009
Příspěvky: 226
Bydliště: Valašsko

PříspěvekZaslal: 24 duben 2009, 12:56    Předmět: Citovat

Mělo by to být nějak takto:

kód:


TMOD = 0x22;    //č/č  0 i 1 v modu 8bit RELOAD
TH0 = 256-100;
TL0 = 256-100;
TR0 = 1;
ET0 = 1;
TH1 = 256-150;
TL1 = 256-100;
TR1 = 1;
ET1 = 1;
EA = 1;




Jinak pokud máš problémy se čtením cizojazyčných návodů,
tak si kup knihu "Práce s mikrokontroléry ATMEL ...." z nakladatelství BEN.
Mají jich tam několik, stačí si vybrat.

_________________
AVR Studio 4.18 + WinAVR, AVR Studio 6.2
Elnec T51prog, ASIX PRESTO, AVR MKII
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu Odeslat e-mail
 

Zobrazit příspěvky z předchozích:   
Zobrazit předchozí téma :: Zobrazit následující téma  
Přidat nové téma   Zaslat odpověď    Obsah fóra mcontrollers.com -> 8051 / 8052 Časy uváděny v GMT + 2 hodiny
 
Strana 1 z 1
Přejdi na:  
Můžete přidat nové téma do tohoto fóra.
Můžete odpovídat na témata v tomto fóru.
Nemůžete upravovat své příspěvky v tomto fóru.
Nemůžete mazat své příspěvky v tomto fóru.
Nemůžete hlasovat v tomto fóru.
Můžete k příspěvkům připojovat soubory
Můžete stahovat a prohlížet přiložené soubory
 



Num Lock Holder - app to hold Numlock
Copyright © 2018 Rudolf Veselý, mcontrollers.com.
Je zakázáno používat části tohoto webu bez souhlasu autora. || Powered by phpBB © 2001, 2002 phpBB Group - with RedSquare DoubleJ(Jan Jaap)