mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Linux, SAM9261, SPI, Pausen bei Übertragung


Autor: Thomas B. (thomasb)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo !

Es geht um folgendes: Ich übertrage unter Linux (das auf einem 
AT91SAM9261 läuft) Daten über die SPI-Schnittstelle an ein Display 
(S65).
Das funktioniert so weit auch problemlos.

Allerdings kam mir die Zeitdauer für die Übertragung eines kompletten 
Screens (46464 Bytes bei 13MHz SPI Takt) etwas lang vor, weswegen ich 
mir das mal mit nem Logic Analyzer angeschaut habe. Dabei ist mir 
aufgefallen, dass zwischen dem eigentlichen Senden eines Words (Dauer: 
~1,3us) immer eine Pause von ungefähr 3.2us vorhanden ist.

Ich benutze dabei die Funktion
int spi_write (struct spi_device *spi,const u8 *buf,size_t len)
,wobei ich den kompletten Speicher (also die 46464 Bytes) auf einmal 
übertragen lasse.

Meine Frage: Welche Möglichkeiten hab ich um die Effizienz der 
Übetragung zu verbessern bzw. konkret die nicht notwendigen Pausen 
zwischen den Übertragungen zu verringern.
Oder komm ich vielleicht mit dieser Schnittstelle von Linux hier gar 
nicht weiter und muss weiter unten am SPI des Prozessors ansetzen 
(spi_writel usw. ) ?

Beschäftige mich noch nicht so lange mit der Linux-Treiberprogrammierung 
und weiß daher nicht so recht wo ich ansetzen kann/soll.

Besten Dank und schöne Grüße,
Thomas B.

: Verschoben durch Admin
Autor: Andreas Schwarz (andreas) (Admin) Benutzerseite Flattr this
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Verwendest du den Treiber atmel_spi? Der unterstützt eigentlich DMA, 
schneller geht's also von Hand auch nicht. Woher die Pause kommt kann 
ich mir da nicht erklären.

Autor: Oliver Döring (odbs)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wo und wie wird die SPI-Schnittstelle initialisiert?

Was wird in das "SPI Chip Select Register" geschrieben, insbesondere in 
das Feld DLYBCT (= "Delay Between Consecutive Transfers")?

Ich habe gerade nur das Datenblatt vom AT91RM9200 vor mir liegen, weil 
ich mich mit dem im Moment herumärgere. Das SPI-Modul dürfte aber 
ähnlich sein. Nur hoffentlich weniger "buggy".

Autor: Thomas B. (thomasb)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Hallo !

Also ob Linux hier den SPI-Treiber aus atmel_spi.c benutzt bin ich mir 
ehrlich gesagt nicht sicher. In der Konfiguration habe ich zwar den 
Atmel-SPI ausgewählt, kann aber in den Linux-Sourcen keinen Aufruf der 
Funktionen aus der atmel_spi.c erkennen (was aber nicht unbedingt etwas 
heißen muss, da ich mich - wie schon erwähnt - noch nicht so lange damit 
beschäftige)

In meinem Board-File hänge ich die spi_board_info-Struktur
static struct spi_board_info testboard_spi_devices[] = {
{ /* User accessible spi - cs1 (1Mhz) */
  .modalias = "s65spi",
  .bus_num = 1,
  .chip_select  = 1,
  .max_speed_hz = 20 * 1000 *  1000,
},
...

mittels folgendem Funktionsaufruf ein:
at91_add_device_spi(testboard_spi_devices, 1);

Diese Funktion ist im File at91sam9261_devices.c realisiert. Dort werden 
scheinbar auch die entsprechenden Pins für die Verwendung als SPI 
konfiguriert:
...
at91_set_A_periph(AT91_PIN_PB30, 0);  /* SPI1_MISO */
at91_set_A_periph(AT91_PIN_PB31, 0);  /* SPI1_MOSI */
at91_set_A_periph(AT91_PIN_PB29, 0);  /* SPI1_SPCK */
...


Bei der Programmierung an sich habe ich mich an die Doku "spi-summary" 
und das Buch "Essential Linux Device Drivers" gehalten. Ich habe dabei 
aber die in der spi-summary angesprochene "Wrapper-Funktion" spi_write 
benutzt, welche das Generieren der spi_messages selber macht.

Anbei auch noch eine Grafik um die Delay-Problematik zu 
veranschaulichen. (Clock=13MHz, Dauer Übertragung: ~1.3us, Pause 
zwischen Übertragungen: ~3.2us)

Schöne Grüße,
Thomas B.

Autor: Oliver Döring (odbs)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Du benutzt atmel_spi.c

Schau dort mal rein, in den Linux-Quellen findest du das unter 
drivers/spi/...

Ich habe nachgeschaut, in das Feld DLYBCT wird tatsächlich eine "0" 
eingetragen, daran liegt es zumindest nicht. Du wirst aber sehen, dass 
der Treiber einige Workarounds um Hardware-Bugs enthält und insgesamt 
nicht gerade schön ist. Zum Beispiel werden die Chipselect-Leitungen per 
GPIO angesteuert. Es gibt auch einige Aufrufe von udelay() in diesem 
Treiber.

Dein Problem wird vermutlich irgendwo dort erzeugt. Vielleicht kannst du 
da ein wenig forschen.

Auf jeden Fall solltest du dich an die Linux4SAM-Mailingliste wenden und 
eine evtl. Problemlösung von dort hier posten.

Autor: Thomas B. (thomasb)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo !

Danke für die Antwort, werde mir die atmel_spi.c mal etwas genauer 
anschauen und das Problem (oder "Feature" ?) bei Linux4Sam bzw. At91.com 
posten.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.