Teplotní senzor LM92-jak přistupovat a zapisovat do registru

Dobrý den,
pomohl by mi prosím někdo, jak číst teplotu ze snímače LM92 pomocí 8051? Podle datasheetu bych měl nastavit do osmibitového registru snímače samé nuly, pokud chci jen číst teplotu. Jenže nevím, jak do registru zapisovat, nebo spíše, kterými piny do něj přistupovat.

Děkuji za pomoc

:arrow_right: administrator: přejmenováno z “Teplotní senzor LM92”

:arrow_right: administrator: přiloženy externí soubory
LM92.pdf (463 KB)

No podle datasheetu se jedná o dvouvodičovou sériovou sběrnici I2C, zkusil bych tedy přístup přes piny SDA a SCL.

Děkuju za odpověď! Takže chápu to správně, že nejdříve pošlu jeden byte nuly na ten SDA (tím nastavím registr, že chci jen číst) a poté už stejným pinem přijímám dva byty s naměřenou teplotou a poté zase celý proces znovu?

no teoreticky tie nuly mozes vynechat… totiz pri zapnuti je ten register nastaveny na default a tym padom citas priamo teplotu

Nezapomeň poslat adresu obvodu, tu která je vytvořena pomocí pinů A0 a A1, aby bylo jasné s kterým čidlem chceš komunikovat.

Děkuji za pomoc! Díky ní jsem se pokusil napsat program, který by měl teplotu ze senzoru číst, bohužel se tak neděje. Nevěděli byste prosím, v čem je chyba? Nevím, jestli jsem správně pochopil funkci “acků”, ale chyba může být zřejmě kdekoliv (kompilace proběhla v pořádku).

Snímač jsem zapojil tak, že piny SDA a SCL jsou na pinu 0 a 1 portu 1. Připojil jsem je tam přímo.
Adresové piny A0 a A1 jsem připojil na zem, stejně tak pin GND. Napájecí pin jsem připojil na zdroj 3,3V, rovněž přímo. Ostatní piny snímače jsem nikam nepřipojoval.
Pracuji s vývojovou deskou Smart RF04EB s procesorem CC2430 od Texas Instrument. Piny senzoru jsem tedy spojil s jednotlivými piny na vývojové desce.

[code]
void main(void)
{
P1SEL=0x0; // Nastavení portu 1 na I/O
halBoardInit(); // Inicializace hodin atd.

i2c_init();
i2c_start();
i2c_address(); // Zaslání prvního bytu s adresou snímače
i2c_ack0(); //Ack (SDA=0)
i2c_byteH(); // Načtení prvního bytu a uložení do pole
i2c_ack0(); //Ack (SDA=0)
i2c_byteL(); // Načtení druhého bytu a uložení do pole
i2c_ack1(); //Ack (SDA=1)
i2c_stop();
}

void i2c_delay(void) // Funkce pro zpoždení 0,3ms, 0,3ms jsem zvolil podle datasheetu, //kde je rozmezí této pauzi do 0,5ms
{halMcuWaitUs(300);}

void i2c_init(void) // Inicializace SDA a SCL na 1
{
P1DIR=0x3; //Nastavení pinů portu 1 na output
SCL=1;
i2c_delay();
SDA=1;
i2c_delay();
}

void i2c_start(void) //Start bit
{
SDA=1;
i2c_delay();
SCL=1;
i2c_delay();
SDA=0;
i2c_delay();
SCL=0;
i2c_delay();
}

void i2c_stop(void) //Stop bit
{
SDA=0;
i2c_delay();
SCL=1;
i2c_delay();
SDA=1;
i2c_delay();
}

void i2c_clock(void) // Jeden impulz hodin
{
SCL=1;
i2c_delay();
SCL=0;
i2c_delay();
}

void i2c_address(void) // Zaslání adresového bytu
{
SDA=1;
i2c_clock();
SDA=0;
i2c_clock();
SDA=0;
i2c_clock();
SDA=1;
i2c_clock();
SDA=0;
i2c_clock();
SDA=0; //Adresa A1 (spojena se zemí)
i2c_clock();
SDA=1; //Adresa A2 (spojena se zemí)
i2c_clock();
SDA=0; //R/W nastaveno na 0,tedy read
i2c_clock();
}

void i2c_ack0(void) // Ack 0
{
SDA=0;
i2c_clock();
}

void i2c_ack1(void) // Ack 1
{
SDA=1;
i2c_clock();
}

void i2c_byteH(void) // Přečtení a nahrátí prvního bytu do pole
{
P1DIR=0x0; //Nastavení pinù na input
int j=0;
while(j!=8)
{
a_i2c_byteH[j]=SDA;
i2c_clock();
j++;
}
}

void i2c_byteL(void) // Přečtení a nahrátí druhého bytu do pole
{
int j=0;
while(j!=8)
{
a_i2c_byteL[j]=SDA;
i2c_clock();
j++;
}
}[/code]

SDA=1; //Adresa A2 (spojena se zemí) —preco davas log1 ked to mas na GND spojene

Neviem ako rychlo to taktujes ale mal by si pouzit doporiucene pullup odpory 4k7 na sda, clk (pravdepodobne teraz pouzivas interne ? )

Děkuju, toho sem si nevšiml, i tak to ale nejde.
Frekvence je 32kHz. Rezistor tam nějaký vnitřní pokud se nepletu je, ale jistě to nevím. Zkusím tam dát tedy ještě ty pullup rezistory. A ty acky jsou správně prosím?

Tak vnitřní pullup odpory tam jsou. Jestli jsem to ale pochopil správně, tak v datasheetu o senzoru (tabulka na straně 2.) nepíší, že by měli být na SDA a SCL. Každopádně na pinech s nimi i bez nich to nejde, do polí se uloží samé jedničky :frowning:

Aha ,takto ack posiela slave t j to cidlo…tj ked posles adresu cidla 8b tak scl nahod do jednotky to je ten 9bit a testuj ci prislo ack od lm cidla tj while sda; potm nastav scl do nuly , oyaj neyabudni nastavit sda na vstup pred tzm ako nastavis 9 bit…

Tak se mi konečně podařilo rozjet komunikaci, bohužel se vyskytl další problém. Snímač vrací vrchní byte a jen jeden bit z nižšího bytu (tedy 9bitů,když nepočítám ack, např 000011000-1111111), poté už zůstane na hodnotě log.1. Změřím tedy teplotu s přesností pouze celého stupně (když si odmyslím zbývající jedničky na konci nižšího bytu). Nevíte prosím, čím to může být? Mohlo by to být tím, že mezi napájením a zemí nemám kondenzátor? Děkuji za případnou odpověd!