Forum: Mikrocontroller und Digitale Elektronik SPDIF empfangen per DMA mit einem STM32F769


von Dieter S. (dsteinwe)


Lesenswert?

Hallo liebe Entwicklergemeinde,

ich Mühe mich jetzt leider schon einige Wochen damit ab, einen 
fehlerfreien und bit-genauen Datenstrom per SPDIF mit dem STM32F769 zu 
empfangen. Als Entwicklungshardware kommt das Eval-Board 
32F769IDISCOVERY 
(http://www.st.com/en/evaluation-tools/32f769idiscovery.html) zum 
Einsatz. Die MCU hat selber einen SPDIFRX-Unit, die ich auch nutzen 
möchte, um nicht noch mehr Silikon zu verschwenden. Wenn ich die 
SPDIFRX-Unit per HAL/Poll anspreche, bekomme ich die Daten wie erwartet: 
Je Subframe ein 32bit Wert. Ich möchte für meine spätere Anwendung gerne 
die Unit aber per HAL/DMA ansprechen und damit habe ich Probleme:

1. Nur jedes 8. Feld im Array des DMA-Empfangsbuffers enthält ein 
SPDIF-Subframe. Es hat mich viel Zeit gekostet, dieses herauszufinden 
und ist so nicht dokumentiert! Die Daten sind valide - das habe ich 
schon kontrolliert. Mir ist nur schleierhaft, welche Funktion die 
anderen 7 Felder haben, vorallem weil dieses Verhalten nicht in der 
MCU/HAL-Spezifikation beschrieben ist. Hat jemand gleiche Erfahrung 
gemacht bzw. diese Unit ebenfalls per DMA benutzt?

2. Die maximale Buffergröße beschränkt sich auf 256 Felder, was bei nur 
jedem achten Feld mit einem Subframe dazu führt, dass bei einem 
Callback-Aufruf effektiv nur 16 (=256  2 Buffer  8 wegen Nutzdaten) 
Subframes empfangen werden können. Ich hätte da gerne mehr Daten, da 
wahrscheinlich dadurch wiederum Timing-Probleme entstehen und 
Verarbeitungsfehler verursacht. Die Grenze von 256 habe ich durch 
Ausprobieren ermittelt. Gibt es einen Grund für diese Grenze? Kann man 
irgendwie noch mehr Speicher benutzen?

Gerne stelle ich bei Bedarf noch mehr Informationen zur Verfügung; ich 
wollte den initialen Post dieses Threads nicht gleich schon so 
aufblähen. Ich hoffe, Ihr habt dafür Verständnis und würde mich über 
Eure Hilfe sehr freuen.

PS: Auch verschiedene Google-Anfragen haben bisher noch kein 
Beispiel-Code für DMA geliefert sondern nur für Polling.

von sPDiF (Gast)


Lesenswert?

Dieter S. schrieb:

> PS: Auch verschiedene Google-Anfragen haben bisher noch kein
> Beispiel-Code für DMA geliefert sondern nur für Polling.

https://github.com/cnoviello/stm32-discof7/blob/master/stm32-discof7-lcddim/system/src/stm32f7xx/stm32f7xx_hal_spdifrx.c

..
+ DMA transfers management
..

von sPDiF (Gast)


Lesenswert?


Beitrag #5070361 wurde von einem Moderator gelöscht.
von Dieter S. (dsteinwe)


Lesenswert?

Lieber sPDiF (Gast),

ich danke Dir für Deine rasche Antwort und Recherchen!


Zum Link: 
https://github.com/cnoviello/stm32-discof7/blob/master/stm32-discof7-lcddim/system/src/stm32f7xx/stm32f7xx_hal_spdifrx.c

Hierbei handelt es sich um die HAL-Implementierung, die ich in meinem 
Code nutze. Ich habe in die HAL-Implementierung schon hineingeschaut und 
natürlich auch in die zugehörige Dokumentation, allerdings konnte ich 
daraus meine Fragen nicht beantworten. Kleine Anekdote am Rande: Der 
Autor Noviello hat übrigens zum STM32 ein e-Book geschrieben. Ich habe 
gefragt, ob er auch ein Kapitel zu SPDIFRX schreiben könnte. Seine 
Antwort: Er kennt sich damit nicht aus. (siehe: 
http://www.carminenoviello.com/mastering-stm32/forums/search/spdif/)


Zum Link: 
https://github.com/torvalds/linux/blob/0b49ce5a40702bf78a5f80076312b244785e9a2f/sound/soc/stm/stm32_spdifrx.c

Den Code kannte ich tatsächlich noch nicht. Ich habe gestern und heute 
den Code schon studiert, allerdings konnte ich daraus bisher noch keine 
neuen Erkenntnisse gewinnen, da es sich nicht um ein eigenständig 
lauffähiges Programm sondern eine ALSA-Implementierung handelt und 
leider meine Programmierfähigkeiten im Bereich STM32 noch ausbaufähig 
sind. Ich arbeite aber daran!



Falls jemand bereit ist, meine ca. 400 Zeilen Code anzuschauen, stelle 
diesen hier gerne ein. Ich bin für jede Hilfe dankbar!

von Dieter S. (dsteinwe)


Angehängte Dateien:

Lesenswert?

Ok, ich habe nun zur Kenntnis genommen, dass man Code als Anhang zur 
Verfügung stellen kann. Gelesen - Getan!

Ebenfalls habe ich meine Test Wav-Datei angehängt. Bitte nicht wundern, 
dass die WAV-Datei in einem 7z-Archiv vorliegt. Diese 
Kompressionsmethode hat als einzige die 560MB in eine akzeptable Größe 
von nur 88KB reduziert!

Wer die Wav-Datei ausprobieren will, sollte diese z.B. unter Windows mit 
dem Programm Winyl abspielen. Bei diesem Programm kann man ein 
spdif-fähiges WASAPI-Audio Device wählen, so dass der Windows-Mixer 
nicht dazwischen grätscht und das Signal kaputt macht. Alternativ auf CD 
brennen und über einen CD-Player mit SPDIF abspielen. So mache ich das.

von Dieter (Gast)


Lesenswert?

Dieter S. schrieb:
> Wer die Wav-Datei ausprobieren will, sollte diese z.B. unter Windows mit
> dem Programm Winyl abspielen. Bei diesem Programm kann man ein
> spdif-fähiges WASAPI-Audio Device wählen, so dass der Windows-Mixer
> nicht dazwischen grätscht und das Signal kaputt macht. Alternativ auf CD
> brennen und über einen CD-Player mit SPDIF abspielen. So mache ich das.

Geht auch problemlos mit div. Programmen wie mpc-be/mpc-hq usw., diese 
bieten in den Audioeinstellungen direkte SPDIF Ausgabe an.

Ohne deinen Code jetzt zu checken: 44100/48000 usw. kontrolliert ob das 
alles passt?

von 2⁵ (Gast)


Lesenswert?

Hast du schon probiert, den Autor des Audio Treiber zu mailen?
Aus dem Programmcode:
[...]
* Author(s): Olivier Moysan <olivier.moysan@st.com> for 
STMicroelectronics.
[...]

von Dieter S. (dsteinwe)


Lesenswert?

> Ohne deinen Code jetzt zu checken: 44100/48000 usw. kontrolliert ob das
> alles passt?

Ich kann mit Sicherheit sagen, dass eine falsche Samplerate nicht die 
Ursache ist.

von Dieter S. (dsteinwe)


Lesenswert?

2⁵ schrieb:
> Hast du schon probiert, den Autor des Audio Treiber zu mailen?

Darüber habe ich auch schon nachgedacht. Ich überlege mir gerade noch, 
wie ich die Mail formuliere, um die Chance auf eine Antwort zu erhöhen.

: Bearbeitet durch User
von Dieter S. (dsteinwe)


Lesenswert?

Ich habe ihm inzwischen geschrieben, aber noch keine Antwort bekommen.

von Dieter S. (dsteinwe)


Lesenswert?

Ich habe Ursache gefunden. Folgende Zeile habe ich geändert:

hdma_rx.Init.PeriphInc = DMA_PINC_DISABLE;

Nun wird alles gut ...

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.