Hallo Nicolas
Bist du mittlerweile weitergekommen?
Ich hab mich in letzter Zeit ein bisschen mit dem MAX1168 auseinander
gesetzt. Ich habe den MAX1168 mit Hilfe der SPI-Schnittstelle im
Controller (bei mir ATmega2561) angesteuert. Das hat zwar nicht auf
Anhieb funktioniert aber mitterweile läuft es problemlos. Wenn du willst
kann ich den Code hier posten.
Auf jeden Fall ist es wichtig am MAX1168 den Pin DSEL auf GND und DSPR
auf High zu legen. Ansonsten rührt sich der MAX1168 nicht.
Insgesamt steig ich durch deinen Code nicht so recht durch da du so gut
wie keine Kommentare nutzt. Was z.B. bedeutet bei SPI_send16(int chip,
char high, char low) chip, high und low?
Ich empfehle dir deine Routine SPI_send8 zu nutzen die ist im Ansatz
schon richtig allerdings dürfte der Aufruf von
1 | CONV_PORT = (1 << chip);
|
2 | CONV_PORT &= ~(1 << chip);
|
am Anfang und Ende von SPI_send8 zu Problemen führen. Ich denke diese
beiden Zeilen sollen so eine Art Chip-Select sein oder? Wenn du dir das
Datenblatt ansiehst so findest du auf Seite 17 und Folgende dass während
der Kommunikation das CS-Signal dauerhaft auf low sein muss. Der
kurzeitige High-Impuls wirkt wahrscheinlich wie ein Reset für den
MAX1168. Außerdem verhindert er dass der MAX1168 das samplen und
konvertieren der AD-Kanäle beginnt.
Im Prinzip ist die Kommunikation mit dem MAX1168 nicht sonderlich
kompliziert (als Beispiel die Kommunikations-Sequenz in Figure 14 auf
Seite 19 im Datenblatt, so habe ich es verwendet):
1. /CS von high nach low schalten
2. Konfigurations-Register mit MSB zuerst an den MAX1168 senden, bei mir
ist es folgendermaßen konfiguriert:
1 | CCC_MAX1168 = (1<<CH_SEL2)|(1<<CH_SEL1)|(1<<CH_SEL0)|(0<<SCAN1)|(1<<SCAN0)|(0<<REF_PDSEL1)|(0<<REF_PDSEL0)|(1<<INT_EXT_CLK);
|
3. warten bis der MAX1168 das /EOC auf low setzt --> Konvertierung zu
Ende
4. Nacheinander die n mal 16 bit reintakten. Das n ergibt sich aus der
konfiguration von (1<<CH_SEL2)|(1<<CH_SEL1)|(1<<CH_SEL0) und
(0<<SCAN1)|(1<<SCAN0). Näheres dazu findest du im Datenblatt. Bei mir
ist es so konfiguriert, dass er alle 8 Kanäle sampled und diese
überträgt, es müssen also 8 x 16 bit übertragen werden.
5. /CS wieder auf high setzen
Wichtig ist wie schon erwähnt, dass Pin DSEL auf GND und DSPR auf High
liegen.
Damit deine SPI-Routine nicht zu schnell taktet kannst du ja ein paar
NOPs einbauen:
1 | void SPI_send8(int chip, char c) {
|
2 | CONV_PORT = (1 << chip);
|
3 | CONV_PORT &= ~(1 << chip);
|
4 |
|
5 | int bit;
|
6 | unsigned int shift = 128;
|
7 | for (bit = 0; bit < 8; bit++) {
|
8 | if (shift & c) {
|
9 | CONV_PORT |= (1 << CONV_MOSI);
|
10 | } else {
|
11 | CONV_PORT &= ~(1 << CONV_MOSI);
|
12 | }
|
13 | shift = shift >> 1;
|
14 | asm ("nop");
|
15 | asm ("nop");
|
16 | asm ("nop");
|
17 | CONV_PORT |= (1 << CONV_SCLK);
|
18 | asm ("nop");
|
19 | asm ("nop");
|
20 | asm ("nop");
|
21 | CONV_PORT &= ~(1 << CONV_SCLK);
|
22 | }
|
23 | SPI_values[chip].low = c;
|
24 |
|
25 | CONV_PORT = (1 << chip);
|
26 | CONV_PORT &= ~(1 << chip);
|
27 | }
|
Das sollte reichen bei 8MHz Taktfrequenz.
Also dann viel Erfolg.
Viele Grüße,
Felix