Ich bin gerade am debuggen einer SPI-Konfiguration, die sich gerade
recht eigenwillig verhält - und schuld ist mit ziemlicher sicherheit
mein code/die µC config:
Ein ATSAM4S als Master mit zwei Slaves (ein ADC und ein Accelerometer)
mit jeweils eigenen CS, die jedoch
a) verschiedene Clockrates (1MHz und 2MHz) und
b) verschiedene SPI modes (Mode 1 und Mode 3)
benutzen.
Für die Implementierung habe ich den Atmel Software Framework mit seinen
spi/spi_master routines genutzt.
Der spi_master_setup_device routine gibt man baudrate, flags, chip
select ids etc und bekommt eine device descriptor struct zurück, die man
dann für weitere spi funktionen nutzt um das zu nutzende spi slave
device zu spezifizieren.
Das hat irgendwann auch schonmal funktioniert, der ADC und das ACCEL
konnten nacheinander angefragt werden und haben daten übertragen, mit
open-bench logic sniffer auch sichtbar gemacht.
Nun habe ich aber folgendes problem: Mit der implementierung, wie sie
nun steht, frage ich in der main loop die jeweils von den slaves
bereitgestelten DataReady (DRDY) Pinlevels ab - und wenn das jeweilige
DRDY high ist, hole ich über spi die daten vom slave:
1 | /*** GET MEASUREMENTS ***/
|
2 | if(dev_status.running){
|
3 | if (SLAVE1.is_enabled){
|
4 | //In case of SLAVE1 DATA READY signal: Get data package
|
5 | if (ioport_get_pin_level(SLAVE1_INT1_GPIO)){
|
6 | // Gets data via SPI
|
7 | slave1_get_measurement(SLAVE1, &adxl_buf, g_ul_ms_ticks);
|
8 | printf("#ACCEL: \t X: \t %d \t Y: \t %d \t Z: \t %d \t time: \t %lu \r\n", adxl_buf.x, adxl_buf.y, adxl_buf.z, adxl_buf.timestamp);
|
9 | }
|
10 | // In case of ADXL ACTIVE Interrupt signal: Send message
|
11 | if (ioport_get_pin_level(SLAVE1_INT2_GPIO)){
|
12 | puts("#Artifact Warning: Active Threshold Interrupt\r\n");
|
13 | slave1_ack_interrupts(SLAVE1);
|
14 | }
|
15 | }
|
16 | if (SLAVE2.is_enabled)
|
17 | {
|
18 | // In case of SLAVE2 DATA READY signal: Get data package via SPI
|
19 | slave2_get_measurement(SLAVE2, &ads_buf, g_ul_ms_ticks);
|
20 | if (ioport_get_pin_level(SLAVE2_INT1_GPIO)){
|
21 | printf("SLAVE2 DATA. T=%lu\r\n",ads_buf.timestamp);
|
22 | for(int i=1; i<9; i++){
|
23 | if (SLAVE2configuration.ch_conf[i-1].usechannel){
|
24 | printf("CH%d: %ld;\r\n", i, ads_buf.ch[i-1]);
|
25 | }
|
26 | }
|
27 | }
|
28 | }
|
29 | }
|
Wie man sieht, kann ich SLAVE1/2 enablen/disablen - einfach über uart
konsole und damit zur übertragung nutzen oder nicht.
Mein Problem nun: Sind beide slaves enabled, schickt mir der ADC nur
mist (nullen und manchmal ne zahl). Habe ich immer nur einen enabled,
dann klappt alles.
Hat da jemand tips? Der ATSAM4S sollte eigentlich in der lage sein
zwischen verschiedenen modes und taktraten hin und herzuschalten (was er
ja auch schon erfolgreich getan hat). Woran kann es liegen?