Witam
Mam kilka pytań związanych z I2C na które nie jestem sobie wstanie odpowiedzieć.
1.
Mam taką funkcę:
Nazwa wskazuje na to że ta funkcja ustawia prędkość, TWSR to rejestr gdzie znajdują się dwa bity TWPS1 i TWPS0 i one ustawiają preskaler a TWBR też służy do podziału.
Zgodnie ze wzorem w pdf mamy:
SCL frequency
CPU Clock frequency/16 + 2(TWBR) ⋅ 4^TWPS
jak działa ta funkcja i jak działa to przeliczenie
speed=(F_CPU/speed/100-16)/2; //speed=TWBR*4^TWPS
a i jescze dlaczego zamiast tego zapisu
TWSR=(TWSR & (_BV(TWPS1)|_BV(TWPS0))) | prescaler;
nie zapisać tego tak
TWSR=prescaler;
2.
Chodzi mi o tą linię dlaczego tam jest I2C_Error==I2C_NoACK przecież w pętli wywołujemy funkcję I2C_SendStartAndSelect a z wnętrza tej funkcji wywołujemy I2C_SendAddr i mamy w niej zapis if(TW_STATUS!=Status) I2C_SetError(I2C_NoACK); else I2C_SetError(I2C_OK); czyli jak jest wszystko ok to tej zmiennej globalnej przypisujemy I2C_OK.
A i to jest pętla więc możemy wysłać kilka razy adres urządzenia chyba nie powinno być to w pętli tylko poza tak abyśmy tylko jeden raz wysłali adres a jak po takim czasie nie dostaniemy ACK od slave to wtedy ponawiamy, nie wiem czy zapis w pętli jest dobry bo my sznurkiem wysyłamy ten sam adres zamiast ustawić jakiś timeout.
Czy nie powinno być tak:
I2C_SendStartAndSelect(addr >> 16);
while(!(I2C_Error==I2C_OK));
3.
W jednej czekamy na wysłanie stop a w drugiej nie dlaczego?
4.
No nieogarniam tych stron tam jest coś takigo że adres bajtu możliwego do zapisu jest wielokrokrotnością tej strony czyli jak mam np. strone 64 bajtową to mogę zapisać bajty pod takie adresy 0,64,128, o to z tym chodzi czy jak działają te strony pamięci w eeprom.
Przepraszam za dużą ilość pytań, kody są z książki Tomasza Francuza. Nie twierdzę że są to błędy tylko pewnie wynika to z moich braków i luk w technikach programowania.
Pozdrawiam
Mam kilka pytań związanych z I2C na które nie jestem sobie wstanie odpowiedzieć.
1.
Mam taką funkcę:
Kod: C / C++
Nazwa wskazuje na to że ta funkcja ustawia prędkość, TWSR to rejestr gdzie znajdują się dwa bity TWPS1 i TWPS0 i one ustawiają preskaler a TWBR też służy do podziału.
Zgodnie ze wzorem w pdf mamy:
SCL frequency
CPU Clock frequency/16 + 2(TWBR) ⋅ 4^TWPS
jak działa ta funkcja i jak działa to przeliczenie
speed=(F_CPU/speed/100-16)/2; //speed=TWBR*4^TWPS
a i jescze dlaczego zamiast tego zapisu
TWSR=(TWSR & (_BV(TWPS1)|_BV(TWPS0))) | prescaler;
nie zapisać tego tak
TWSR=prescaler;
2.
Kod: C / C++
Chodzi mi o tą linię dlaczego tam jest I2C_Error==I2C_NoACK przecież w pętli wywołujemy funkcję I2C_SendStartAndSelect a z wnętrza tej funkcji wywołujemy I2C_SendAddr i mamy w niej zapis if(TW_STATUS!=Status) I2C_SetError(I2C_NoACK); else I2C_SetError(I2C_OK); czyli jak jest wszystko ok to tej zmiennej globalnej przypisujemy I2C_OK.
A i to jest pętla więc możemy wysłać kilka razy adres urządzenia chyba nie powinno być to w pętli tylko poza tak abyśmy tylko jeden raz wysłali adres a jak po takim czasie nie dostaniemy ACK od slave to wtedy ponawiamy, nie wiem czy zapis w pętli jest dobry bo my sznurkiem wysyłamy ten sam adres zamiast ustawić jakiś timeout.
Czy nie powinno być tak:
I2C_SendStartAndSelect(addr >> 16);
while(!(I2C_Error==I2C_OK));
3.
Kod: C / C++
W jednej czekamy na wysłanie stop a w drugiej nie dlaczego?
4.
No nieogarniam tych stron tam jest coś takigo że adres bajtu możliwego do zapisu jest wielokrokrotnością tej strony czyli jak mam np. strone 64 bajtową to mogę zapisać bajty pod takie adresy 0,64,128, o to z tym chodzi czy jak działają te strony pamięci w eeprom.
Przepraszam za dużą ilość pytań, kody są z książki Tomasza Francuza. Nie twierdzę że są to błędy tylko pewnie wynika to z moich braków i luk w technikach programowania.
Pozdrawiam