PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : ADS1211 mit AtMega128 Kommunikationsproblem



thob
17.08.2010, 17:20
Hallo

Ich habe ein Problem, mein ADS1211 mit SPI anzusprechen
Wie man an den Bildern im Anhang sehen kann, funktioniert die Kommunikation von AtMega ausgehend wunderbar, nur die angeforderten Daten kommen nicht zurück (Die Bilder wurden von einen Oszilloskop gemacht) Die rote Linie ist der SCK die blaue Linie zuerst MOSI, dann MISO und dann DRDY
Weiss jemand, wo das Problem liegen könnte? wenn ihr mehr Infos braucht, gebe ich gerne Antwort ;)

Hubert.G
17.08.2010, 17:51
Was geschieht nach dem DRDY Signal?

thob
17.08.2010, 18:47
Hallo
Sobald DRDY wieder auf LOW geht, beginnt der AtMega wieder von vorne mit dem senden einer 0b10000100 (Auslesen des Command Register Byte 3), die Bilder sind immer die gleichen, die ich auf dem Oszi erhalte, d.h. der ADS1211 sendet nie irgendetwas. Ich habe es auch schon mit dem Auslesen anderer Register versucht, bekomme aber auch dort nie eine Antwort.

Hubert.G
17.08.2010, 20:41
Du bekommst doch auf der MISO Daten, nach dem Oszillogramm etwas schwer zu interpretieren.

Hubert.G
17.08.2010, 21:01
Default im Commandregister 3 ist SDL 0, das heisst das die Ein und Ausgabe auf SDIO stattfindet.

thob
17.08.2010, 21:14
Erstmal vielen Dank das du dich meinem Problem annimmst! Echt nett von dir.

Mein Problem ist, das bei MISO (am ADS1211 SDOUT) wie schon von dir gesagt schwer leserliche Daten kommen, diese könnten auch genau so gut durch Zufall, da der Pin als nicht gebraucht deklariert ist, entstanden sein. Auf jeden Fall interpretiert der AtMega die Daten als lauter 0en. Auf dem SDIO - Pin, der eigentlich die Daten liefern müsste, tut sich jedoch gar nichts.
Meinst du die "MISO - Daten" sind tatsächlich die vom AtMega erwarteten Daten? Ich bezweifle es, da der ADS1211 eigentlich laut Datenblatt ein 0b01000000 als Antwort liefern müsste, und ich die weder von SDIO noch von SDOUT erhalte.

Hubert.G
17.08.2010, 21:34
Ich meinte MOSI, oder sendest du zwei mal 8bit, es sieht doch aus als wenn etwas kommen würde, oder ist das was anderes. Da es sich mit SCK überlappt etwas schwer zu erkennen.
Es würde mich nicht wundern wenn man erst das Richtige hineinschreiben muss, damit man was heraus bekommt.

thob
17.08.2010, 21:42
Als bei MOSI schreibe ich zuerst den INSR - Code (0b10000100) und dann 0b00000000, eigentlich nur um den Schreibvorgang zu starten. Was meinst du genau mit "Richtige"? Ich habe im Datenblatt nichts dergleichen gefunden und der normale Weg etwas über SPI zu erhalten ist meines Wissens nach über lauter 0's senden.

Hubert.G
17.08.2010, 21:55
Wenn du lauter 0 sendest, schreibst du ja wieder in das INSR .
MODE und CS wirst du ja richtig beschalten haben.

thob
17.08.2010, 22:01
Ja aber das muss ich ja, wie sonst kann ich die Taktsignale erzeugen? MODE und CS sollten in Ordnung sein, ich glaube nicht das dort das Problem liegt...

thob
17.08.2010, 22:38
Ich habe nun mein Program so abgeändert, dass zuerst wie schon vorhin die ersten 8 bits ins INSR geschrieben werden, dann jedoch SPI disabled wird, MISO und MOSI auf Eingang schaltet und die Taktsignale von mir direkt softwaremässig erzeugt werden. Die "Antwort" auf MISO sieht schon anders aus...

Hubert.G
18.08.2010, 08:33
Versuche doch mal in dieses Command Register 3 zu schreiben, so das MISO funktioniert.
Dann könntest du alles über SPI machen.

thob
19.08.2010, 15:29
Hat leider nichts gebracht, die Bilder des Oszilloskop sind die gleichen. Könnte es sein, dass der Chip kaputt ist? Gibt es eine simple Methode, dies herauszufinden?

Hubert.G
19.08.2010, 16:09
Ich glaube nicht das der Chip so leicht zum kaputt machen ist. Es werden nur ein paar doofe Einstellungen sein warum es nicht geht.

thob
19.08.2010, 17:39
Hoffentlich :) genug teuer war er ja...
Bin nur langsam am verzweifeln, da ich etwa schon seit eine Woche versuche, das Ding zum laufen zu bekommen :(
Merkwürdig kommt mir allerdings vor, dass SDIO und SDOUT die Taktsignale von SCK mit aufsteigender Voltzahl "mitmachen", ist das Normal? (ich habe es auf dem Bild rot markiert)

Hubert.G
19.08.2010, 22:02
Sieht etwas eigenartig aus, im korrekten Betrieb würde es wahrscheinlich komplett untergehen.

BASTIUniversal
22.08.2010, 17:11
Hallo!
Ich denke das es einfacher ginge, wenn du deinen Schaltplan und dein Programm posten würdest. Ansonsten stochert jeder nur im Nebel herum.

Gruß
Basti

thob
24.08.2010, 14:55
Tut mir leid, dass ich so lange nicht geantwortet habe, hatte soeben Prüfungen an der ETH.
Ich habe mal einen Versuch unternommen, einen Schaltplan zu zeichen, ich hoffe er ist genug klar, auch wenn mir bewusst ist, dass es eindeutig besser gehen würde ;)
Das Program wird auf einem ArduinoMega ausgeführt und ist dementsprechend minimal anders als C



#include <avr/io.h>


uint8_t data[] = {0,0,0};

void SPI_init(void)
{
DDRB = ((1<<DDB2)|(1<<DDB1)|(1<<DDB0)); //spi pins on port b MOSI SCK,SS outputs
SPCR = ((1<<SPE)|(1<<MSTR)|(1<<SPR1)); // SPI enable, Master, f/64
}



uint8_t SPI_Transmit(uint8_t cData)
{
SPDR = cData;
while(!(SPSR & (1<<SPIF)))
;
return SPDR;
}

uint8_t SPI_receive()
{
SPCR &= ~(1 << SPE); //disable SPI
DDRB |= ( 1 << DDB1); //set clock to output
DDRB &= ~(1 << DDB2); //set MISO & MOSI to input
DDRB &= ~(1 << DDB3);

PORTB |= (1 << PB1); //generate 8 cycles on SCK
delayMicroseconds(2);
PORTB &= ~(1 << PB1);
delayMicroseconds(2);
PORTB |= (1 << PB1);
delayMicroseconds(2);
PORTB &= ~(1 << PB1);
delayMicroseconds(2);
PORTB |= (1 << PB1);
delayMicroseconds(2);
PORTB &= ~(1 << PB1);
delayMicroseconds(2);
PORTB |= (1 << PB1);
delayMicroseconds(2);
PORTB &= ~(1 << PB1);
delayMicroseconds(2);
PORTB |= (1 << PB1);
delayMicroseconds(2);
PORTB &= ~(1 << PB1);
delayMicroseconds(2);
PORTB |= (1 << PB1);
delayMicroseconds(2);
PORTB &= ~(1 << PB1);
delayMicroseconds(2);
PORTB |= (1 << PB1);
delayMicroseconds(2);
PORTB &= ~(1 << PB1);
delayMicroseconds(2);
PORTB |= (1 << PB1);
delayMicroseconds(2);
PORTB &= ~(1 << PB1);

SPI_init(); //initialise SPI again

return SPDR; //only formal (for later use)

}

void ADS1211_receive()
{
delayMicroseconds(10);
SPI_Transmit(B00000100); //send INSR: write 1 Byte to Command Register Byte 3 (MSB)
delayMicroseconds(5);
SPI_Transmit(B01000010);//send Data: everything default except SDL = 1
delayMicroseconds(5);
SPI_Transmit(B10000100);//send INSR: read 1 Byte (Command Register Byte 3 (MSB))
delayMicroseconds(5);
data[0] = SPI_receive();//receive, expecting B01000010
}

void setup()
{
Serial.begin(9600);
Serial.write("starting up..."); //say hello

DDRL &= ~( 1 << DDL1 ); //set DL1 to input pin for DRDY
SPI_init(); //initialise SPI
delay(1000);
}

void loop()
{
ADS1211_receive();
delayMicroseconds(20);
delay(2);
}

Hubert.G
24.08.2010, 17:37
Ob da für SPI alles richtig konfiguriert wird, kann ich nicht sagen, kenne den Arduino nicht.
Deine Binär-Schreibweise im Receive stört mich allerdings, ich schreibe immer (0b00000100), vielleicht ist der Arduino Compiler grosszügig.

thob
24.08.2010, 18:08
Eigentlich ist Arduino nur eine "Bibliothek", die ein paar Sachen erleichtert, jedoch kann ganz normaler C - Code eingefügt werden. Die SPI - Routinen kann man exakt so auch mit dem gcc kompilieren lassen. Leider funktioniert 0b00000100 oder auch 0x00000100 nicht, Arduino hat es lieber, wenn man B00000100 schreibt ;). Übrigens nutzt Arduino intern den gcc, er baut vorher den Code einfach ein bisschen um...

Hubert.G
24.08.2010, 18:55
Geht wie folgt:

CMR Schreiben:
CS auf Low
SPI_Transmit(0b00000100);
SPI_Transmit(0b01000010); // Setzt SDIO auf output
CS auf High

unsigned char CMRdata;
CS auf Low
SPI_Transmit(0b10000100);
CMRdata=SPI_Transmit(0xff); // Liest CMR Data aus. 0xff ist nur damit der SPI Clock läuft; 0xff wird vom Chip ignoriert
CS auf High

SPI Transmit ist vielleicht etwas irreführend, da es gleichzeitig ein Receive ist.
SPI Transceive wäre treffender.

thob
24.08.2010, 21:24
Habs jetzt mal genau so versucht, wie du beschrieben hast, hab sogar noch den Controller ausgetauscht (gegen ein Crumb64 - Modul), das Program auch noch in reinem C geschrieben, jedoch immer noch genau das gleiche Ergebnis. Ich habe ehrlich gesagt langsam das Gefühl, der Chip ist tatsächlich kaputt :(

(noch eine Frage am Rande: Spielt es eine Rolle, welche Daten man beim Empfangen in SPDR schreibt?)

Hubert.G
24.08.2010, 21:59
Beim Empfangen schreibt man 0xff, da nur das vom Chip ignoriert wird.
An sich sollte der Arduino eine komplette SPI Bibliothek haben.
Wenn sich aber überhaupt nichts tut, werde ich auch etwas skeptisch.