| Passwort vergessen?
Sie sind nicht angemeldet. |  Anmelden

Sprache auswählen:

Wumpus-Gollum-Forum von "Welt der Radios".
Fachforum für Sammler, Interessierte, Bastler
Sie sind nicht angemeldet.
 Anmelden

Software Defined Radio
  •  
 1 2 3 4
 1 2 3 4
23.10.17 15:50
HB9 

WGF-Premiumnutzer

23.10.17 15:50
HB9 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo Bernhard,

das Display ist ein 'Iduino' 2.8" TFT (320*240 Pixel) mit Touch Screen und 8bit-Parallelbus, nach Datenblatt sollte es einen ILI9341-Controller haben, es hat aber einen ILI9325-Controller. Wenn man den Code auf diesen Controller ändert, funktioniert es, falls man die Register 90h..9fh nicht initialisiert.

Für UKW dürfte die Rechenleistung des STM32 nicht reichen, bei FM braucht man ja 150kHz Bandbreite, und für DAB+ ein paar MHz. Alternativ kann man dafür ein FPGA verwenden, die sind durch die parallele Verarbeitung um Grössenordnungen schneller. Aber man kann auf UKW natürlich die NF-Signalverarbeitung (Stereodekoder, RDS) digital erledigen, da reichen 120kHz Samplingfrequenz und die Verarbeitung ist nicht allzu schwierig. Als Stereo-Nachrüstung für einen guten FM-Empfänger durchaus eine Überlegung wert.

Mein Empfänger bekommt vorerst ein einfaches LW-Frontend (0..400kHz), wenn es SW-technisch 'stand alone' betrieben werden kann, dann kann man mal in ungestörter Umgebung Empfangserfahrungen machen. Weiter kann ich auch die ZF eines meiner Röhrenradios anzapfen, dann hat man den direkten Vergleich zwischen analoger und digitaler ZF-Verarbeitung.

Gruss HB9

!
!!! Photos, Graphiken nur über die Upload-Option des Forums.    
!!! Keine Komplett-Schaltbilder, auf denen Urheberrechte Anderer liegen!

Nicht nur den neuesten Beitrag eines Threads lesen.
25.10.17 16:52
joeberesf 

WGF-Premiumnutzer

25.10.17 16:52
joeberesf 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo HB9,

HB9:
Nach diversen Recherchen war dann klar: Im Display war nicht der im Datenblatt angegebene Controller verbaut, sondern ein anderer, der nicht kompatibel ist. So was nenne ich oberfies! Nachdem der Controller enttarnt war, ging es dann recht flott, und mittlerweile habe ich die Library zur Ansteuerung so abgeändert, dass sie auch funktioniert.

das ist ja entsetzlich, aber auch extrem , dass Du diesen Bestückungsfehler erkannt hast und die Library aufgrund deines Wissens ändern konntest. Bei meinen Versuchen verlasse ich mich schon darauf. Ansonsten Blackout! Trotzdem habe ich z.B. bei meinen RTC- Versuchen (Uhr, Clock-Modul), egal welches Display genutzt wird, festgestellt, dass der übliche Eingang A4, A5 beim Mega 2560 nicht wirklich funktioniert. Warum? Klar habe ich die Pins SDA 20 und SCL 21 am Mega 2560, aber warum funktioniert hier nicht auch A4, A5 wie beim UNO. ....keine Ahnung! Selbst das Demo auf meiner CD verweist auf A4, A5! Ein Anfänger kann dann schon mal verzweifeln...oder?

Zurück zum Thema:

ZF, Demodulation etc...hin oder her..., für solch ein Radio mit Controller, würde ich versuchen eine modulare Struktur zu schaffen. Sprich ..
ein Controllerkästchen mit optimalen Display, an dem nur noch ein x- beliebiges HF- Teil angeschlossen wird. Der Rest lauft über eine Programmänderung. AM. FM, CW, SSB... ein Allrounder halt! Die entsprechenden Schnittstellen müssen dazu vorbereitet und natürlich zugänglich sein.

Gruß

Joerg

Zuletzt bearbeitet am 25.10.17 17:08

26.10.17 08:50
HB9 

WGF-Premiumnutzer

26.10.17 08:50
HB9 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo Jörg,

in der Controllerwelt gibt es viele Fallstricke, das ist so. Erschwerend kommt noch hinzu, dass alles sehr schnell gehen muss und daher kaum mehr seriös entwickelt und getestet wird. Da wird schnell mal ein Chip getauscht oder eine Schaltung geändert, ohne die Softwarebibliotheken anzupassen, und schon funktioniert es nicht mehr, wie bei meinem Display und vermutlich auch bei deinem RTC-Problem.

Zum Radio: Schon aus störungstechnischen Gründen wird der Digitalteil ein eigenes Modul, gut verpackt, damit sich das Radio nicht selber stört. Hardware-Schnittstellen gibt es da nicht viele: ZF-Eingang, NF-Ausgang, Debug-Schnittstelle, serielle Schnittstelle für einen allfälligen DDS-Oszillator, wenn man das Frontend durch den Microcontroller abstimmen will, und noch ein paar wenige digitale Ausgänge für Steuerzwecke, z.B. Zuschalten eines Vorverstärkers oder Abschwächers.

Die Software ist modular, da kann man ohne Aufwand eine Funktion (z.B. Demodulator) durch eine andere ersetzen und neu compilieren. Auch Hardwareanpassungen werden so relativ einfach, aus diesem Grund habe ich auch die Bibliothek für die Displaysteuerung stark modifiziert. Neben der Beseitigung der unzähligen Fehler hat es da jetzt keine einzige hardwarespezifische Funktion mehr, die Zugriffsfunktionen auf die Display-Hardware sind jetzt ausgelagert, so dass man nur diese bei einem anderen Display anpassen muss, und da hält sich der Aufwand in Grenzen, sofern die Dokumentation stimmt

Mittlerweise ist die Software für ein Einfach-LW-Radio schon sehr weit gediehen, so dass ich sie hier bald vorstellen kann, zusammen mit einem einfachen LW-Frontend, so kann man auch etwas empfangen. Europa 1 und Luxemburg sollte man ja in ganz Europa empfangen können, und im Norden und Osten ist die Auswahl noch etwas grösser. Alternativ kann man auch die ZF eines 'normalen' AM-Radios einspeisen, die liegen ja fast immer unter 500kHz und haben ausreichend Pegel. In diesem Fall kann natürlich auch gleich der NF-Verstärker zur Wiedergabe genutzt werden.

Damit niemand am Display scheitert, gibt es auch eine Software-Version, die über die serielle Schnittstelle gesteurt werden kann, und der Seriell- nach USB-Adapter ist beim Nucleo-Board ja schon integriert und funktioniert.

Gruss HB9

27.10.17 22:31
joeberesf 

WGF-Premiumnutzer

27.10.17 22:31
joeberesf 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo HB9,

HB9:

Damit niemand am Display scheitert, gibt es auch eine Software-Version, die über die serielle Schnittstelle gesteurt werden kann, und der Seriell- nach USB-Adapter ist beim Nucleo-Board ja schon integriert und funktioniert.


bei der Arduino Plattform ist es ja jeder Zeit möglich den seriellen Monitor als Ausgabe zu aktivieren und mit den entsprechenden Befehlen die gewünschten Daten auf dem Monitor anzuzeigen. Nun habe ich festgestellt, dass ein Anschluss am Board, hier über USB, die Laufzeit des Programms beeinflusst. Häufig benutze ich die Schnittstelle ja nur als Spannungseinspeisung 5V, aber auch hier ist mir das schon aufgefallen......ich meine ohne den seriellen Monitor zu aktivieren! Ich setze dann eine externe Quelle (Batterie oder Netzteil) und das Problem ist behoben. Kennst Du dieses Phänomen auch?

Gruß

Joerg

29.10.17 12:28
HB9 

WGF-Premiumnutzer

29.10.17 12:28
HB9 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo zusammen,

nun kommt die Praxis.

Zu Jörg: Ich kenne die 'originalen' Arduinos nicht und weiss daher auch nicht, wie dort die Kommunikation genau funktioniert. Beim Nucleo-Board hat die serielle Schnittstelle gar nichts mit dem Debugger zu tun und beeinflusst somit auch die Performance nicht. Somit kann man sie mit gutem Gewissen nutzen, und unter Windows erscheint sie als COM-Port, so dass man mit jedem beliebigen Terminalprogramm darauf zugreifen kann. Die Seriell- nach USB-Umsetzung macht dabei der Debugger-Chip und nicht der STM32.

Also los geht's! Gebraucht wird das Nucleo-Board STM32F446RE von STMicro, ein HF-Frontend und bei Bedarf ein LCD mit 320*240 Zeichen, Touch Screen, 8Bit-Parallelbus und dem ILI 9325-Controller. Ich habe das Display von 'TF028' von 'Iduino' verwendet, das kann direkt auf die Arduino-Schnittstelle des Nucleo-Boards gesteckt werden. Wenn man die Software anpasst, gehen auch andere Displays.

Zum Anschluss: Der HF-Eingang ist Port PA6 und der NF-Ausgang ist Port PA5. Da beim Nucleo-Board an PA5 die 'User LED' angeschlossen ist, muss man diese abhängen (Vorwiderstand auslöten, ist im Nucleo-Manual beschrieben). Die 3.3V findet man ebenfalls in dieser Gegend, und auch einen Ground-Pin. Am besten verwendet man hier eine ein- oder zweireihige Buchsenleiste, die auf CN10 gesteckt wird. Da es nur 4 Pins sind, die gebraucht werden, und diese erst noch in einer Reihe direkt nebeneinander sind, reicht eine 4-polige Buchsenleiste.

Nun zum HF-Frontend. Eine Simpel-Lösung habe ich im PDF 'HF simpel.pdf' angehängt. L1 ist eine Ferritantenne, alternativ geht auch ein Topfkern mit Koppelspule für eine Aussenantenne. Die Windungszahl richtet sich nach der Empfangsfrequenz, möglich ist LW oder auch auf den Aliasing-Frequenzen MW und untere KW, solange man von den Vielfachen von 500kHz ausreichend Abstand hält.
Der FET dient als hochohmiger Puffer und Verstärker. Die 3.3V für die Offseteinstellung vom A/D-Wandler kann man am Nucleo-Board anzapfen. Die 8..12V müssen sauber sein.
Zapft man die ZF eines Empfängers an, wird statt dem Schwingkreis L1/C1 ein 1M-Widerstand vom Gate nach Masse geschaltet und die ZF über einen kleinen Koppelkondensator (1..10pF) eingekoppelt. Bei Röhrengeräten muss man nicht einmal im Gerät herumlöten, da reicht eine Metallkappe auf der ZF-Röhre:



Das abgeschirmte Kabel soll möglichst kurz sein. Besser ist es, den FET direkt beim Empfänger zu platzieren und den Drain-Anschluss über ein abgeschirmtes Kabel zum Rest der Schaltung zu führen.

Hier noch das Gespann in Aktion, als Empfänger dient ein Paillard mit Jahrgang 1952:



Nun zur Software. Da man keine Zip-Dateien hochladen kann, habe ich die Sourcefiles einzeln angehängt. Nach dem Download wird die Endung '.txt' entfernt. Weiter braucht man das Atollic TrueStudio Lite, das es kostenlos im Internet gibt.

Hat man das TrueStudio installiert und gestartet, erstellt man ein leeres C++-Projekt für das Nucleo-Board (wird direkt unterstützt). Danach kopiert man die Sourcefiles (ohne die Endung .txt) in den Ordner 'src' des neu erstellten Projekts, dabei werden ein paar Dateien überschrieben, das ist so korrekt. Danach sollte man compilieren können. Wichtig ist noch, bei den Debugger-Einstellungen 'SWD' zu aktivieren, der Rest sollte stimmen. Das Manual liefert bei Problemen Hilfe, ist aber recht umfangreich.

Zur Funktion der Software:
Nach dem Start (dauert ca. 5 Sekunden) ist die Frequenz 183kHz und Bandbreite 4.5kHz ausgewählt, so dass man Europa 1 empfangen kann.
Man kann über die serielle Schnittstelle die Frequenz und Bandbreite einstellen, dazu sendet man ein kleines 'b' (für Bandbreite) oder 'f' für Frequenz, gefolgt von Enter. Nun gibt man die Bandbreite in 100Hz-Einheiten (also 5..99) oder die Frequenz in Hz ein, Abschluss mit Enter.
Die Bedienung über das Display sollte klar sein, der Button 'weitere Funktionen' und die Modulationswahl in der untersten Zeile haben noch keine Funktion. Die Performance des Displays ist noch mässig, aber es gibt Verbesserungspotential, sowohl auf der HW- als auch auf der SW-Seite, so dass die Reaktion schneller erfolgt, insbesondere beim Neuzeichnen grösserer Flächen.

Hier noch ein Bild vom Displayinhalt:



Gruss HB9

Zuletzt bearbeitet am 29.10.17 13:28

Datei-Anhänge
HF simpel.pdf HF simpel.pdf (15x)

Mime-Type: application/pdf, 11 kB

ADC_Interrupt_asm.s.txt ADC_Interrupt_asm.s.txt (12x)

Mime-Type: text/plain, 11 kB

ADC_Interrupt.cpp.cpp.txt ADC_Interrupt.cpp.cpp.txt (10x)

Mime-Type: text/plain, 8 kB

ADC_Interrupt.h.txt ADC_Interrupt.h.txt (10x)

Mime-Type: text/plain, 1 kB

AGCcoeff.c.txt AGCcoeff.c.txt (10x)

Mime-Type: text/plain, 1 kB

CPU_init.cpp.txt CPU_init.cpp.txt (9x)

Mime-Type: text/plain, 6 kB

CPU_init.h.txt CPU_init.h.txt (9x)

Mime-Type: text/plain, 1 kB

Filterkoeffizienten.cpp.txt Filterkoeffizienten.cpp.txt (9x)

Mime-Type: text/plain, 30 kB

font.c.txt font.c.txt (9x)

Mime-Type: text/plain, 5 kB

LCD.cpp.txt LCD.cpp.txt (11x)

Mime-Type: text/plain, 11 kB

LCD.h.txt LCD.h.txt (9x)

Mime-Type: text/plain, 1 kB

main.cpp.txt main.cpp.txt (9x)

Mime-Type: text/plain, 2 kB

menu.cpp.txt menu.cpp.txt (8x)

Mime-Type: text/plain, 13 kB

menu.h.txt menu.h.txt (9x)

Mime-Type: text/plain, 1 kB

NF_HP.c.txt NF_HP.c.txt (9x)

Mime-Type: text/plain, 1 kB

startup_stm32f446xx.s.txt startup_stm32f446xx.s.txt (9x)

Mime-Type: text/plain, 26 kB

stm32f4xx_hal_conf.h.txt stm32f4xx_hal_conf.h.txt (9x)

Mime-Type: text/plain, 18 kB

system_stm32f4xx.c.txt system_stm32f4xx.c.txt (9x)

Mime-Type: text/plain, 20 kB

TFTv2.cpp.txt TFTv2.cpp.txt (9x)

Mime-Type: text/plain, 13 kB

TFTv2.h.txt TFTv2.h.txt (10x)

Mime-Type: text/plain, 4 kB

usart2.cpp.txt usart2.cpp.txt (9x)

Mime-Type: text/plain, 2 kB

usart2.h.txt usart2.h.txt (9x)

Mime-Type: text/plain, 1 kB

Display.jpg Display.jpg (8x)

Mime-Type: image/jpeg, 51 kB

ZF Empfang.jpg ZF Empfang.jpg (9x)

Mime-Type: image/jpeg, 126 kB

Ankopplung.jpg Ankopplung.jpg (8x)

Mime-Type: image/jpeg, 57 kB

29.10.17 13:23
HB9 

WGF-Premiumnutzer

29.10.17 13:23
HB9 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo zusammen,

hier noch eine kurze Beschreibung der Software, damit man sich etwas besser orientieren kann.

Die Funktion 'main' in main.cpp initialisiert die CPU und bedient danach in einer Endlosschleife das Display und die serielle Schnittstelle. Dabei wird davon ausgegangen, dass nur eine der beiden Bedienmöglichkeiten aufs Mal genutzt wird, daher wird bei Eingaben über eine Schnittstelle die andere blockiert.

Im File 'TFTv2.cpp' sind die Displayfunktionen implementiert, diese stammen grösstenteils vom Paket 'UTFT', das als Open-Source frei heruntergeladen werden kann. Den hardwarespezifischen Teil habe ich in das File 'LCD.cpp' ausgelagert, so dass es neu displayunabhängig wird. Weiter habe ich diverse Fehler korrigiert. Im zugehörigen Headerfile (TFTv2.h) sind die Funktions-Prototypen.

Im File 'LCD.cpp' sind alle hardwarespezifischen Funktionen zur Ansteuerung des Displays vorhanden, im zugehörigen Headerfile sind die exportierten Funktionen, die nicht mehr von der Hardware abhängig sind. Für ein anderes Display muss daher 'LCD.cpp' angepasst werden, eventuell auch 'CPU_init.cpp', dort werden die Schnittstellen initialisiert.

'USART.cpp' mit zugehörigem Header bietet einfache Funktionen für die serielle Schnittstelle zwecks Debugging. Sie ist bewusst einfach gehalten und nutzt daher weder DMA noch Interrupts, daher können Zeichen verlorengehen, wenn der PC zu schnell sendet. Die Schnittstelle ist auf 112.5kBaud, 8 Datenbits, keine Parität und 1 Stoppbit initialisiert.

In 'ADC_Interrupt.cpp' wird die eigentliche Empfangsfunktion ausgeführt, zudem sind dort noch ein paar Initialisierungsfunktionen, z.B. für das Erstellen der Sinustabelle. Der DMA-Interrupt, der immer nach 20 Samples vom A/D-Wandler ausgelöst wird, ruft dabei die Funktion 'ADC_DMA_Interrupthandler' auf, welche die 20 Samples verarbeitet und ein neues Sample auf dem D/A-Wandler ausgibt. Im File 'ADC_Interrupt_asm.s' sind die zeitkritischen Funktionen in Assembler implementiert, und zwar:
ADC_INT: NCO, Mischer und CIC-Filter vom I- und Q-Kanal, Rückgabewert ist ein I- und ein Q-Sample
BiQuad_Stage_asm: Berechnung einer BiQuad-Stufe (gleich wie die C-Funktion 'BiQuad_Stage', aber doppelt so schnell)

Für das Verständnis der Assemblerfunktionen: Allfällige Aufrufparameter werden in den Registern s0..s3 (für Parameter vom Typ 'float') und r0..r3 (für alle übrigen Typen bis 32 Bit) in der Reihenfolge des C-Aufrufs übergeben. Allfällige Rückgabewerte muss die Assemblerfunktion in s0 (float) oder r0 (alle übrigen Datentypen) schreiben.

'Menu.cpp' ist für die Darstellung und Auswertung der Bedienelemente zuständig und bestimmt somit das Aussehen.

'startup_stm32f446xx.s' ist das eigentliche Startupfile, hier sind die Interruptvektoren definiert und hier wird auch das RAM initialisiert, die statischen Konstruktoren aufgerufen und danach nach 'main' gesprungen. Dieses File ist im TrueStudio bereits vorhanden, es musste aber noch der Interrupthandler für den DMA-Interrupt eingetragen werden, daher muss es ersetzt werden.

Die übrigen C-Files definieren Konstanten für die Filter und den Displayfont.

Noch zur Nutzung der CPU-Peripherie (ist auch im File 'CPU_Init.cpp' ersichtlich):

Timer 2: läuft frei mit 10kHz und wird für Zeitmessungen und Verzögerungen genutzt

Timer 4: liefert den 1MHz-Samplingtakt für den A/D-Wandler

Timer 5: liefert den 50kHz-Samplingtakt für den D/A-Wandler

DMA2: Hier wird Channel 0 /Stream 0 für den Transfer der Samples vom A/D-Wandler in die Variable 'ADC_DMA_Buffer' benutzt. Nach 20 Samples wird ein Interrupt ausgelöst (Funktion 'ADC_DMA_Interrupthandler'), der die Verarbeitung der 20 Samples macht.

ADC1: Samplingfrequenz 1MHz von Timer 4, wandelt das HF-Empfangssignal

ADC2: liest Position des Touch-Screens, wird bei Bedarf durch die Software bedient

DAC2: Ausgabe der NF

Das Display wird über GPIOs angesteuert. Da die 8 Datenbits von 3 verschiedenen Ports stammen und auch nicht der Reihe nach angeordnet sind, ist das ziemlich ineffizient. Hier mache ich mal eine Trägerplatine mit neuen Verbindungen, so dass alle Datenbits vom selben Port und lückenlos aufeinanderfolgen.

Gruss HB9

05.11.17 17:14
HB9 

WGF-Premiumnutzer

05.11.17 17:14
HB9 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo zusammen,

es geht weiter. So wie es sich für Software gehört, gibt es hier ein Update mit folgenden Änderungen:

- Funktion von Timer 4 übernimmt jetzt Timer 3, so kann Timer 4 später für einen Dreh-Encoder für die Abstimmung verwendet werden.
- Interrupthandler optimiert, jetzt belastet er die CPU nur noch mit 50..60%, dadurch wird Display wesentlich schneller.
- Die fehlenden Modulationsarten eingebaut (AM synchron, USB, LSB, CW), CW vorerst mit minimaler Bandbreite von 1kHz.
- AGC für USB, LSB und CW mit langsamen Abfall.
- Balken der Feldstärkeanzeige wird schneller aktualisiert und reagiert jetzt fast verzögerungsfrei.
- Zahl der Pegelanzeige wird bei Übersteuerung des ADC rot.
- Statt der Tiefpass-Eckfrequenz wird die tatsächliche ZF-Bandbreite (=2*Eckfrequenz) angezeigt.

Die geänderten Files sind im Anhang, einfach die Endung '.txt' entfernen und die restlichen Files vom vorletzten Beitrag nehmen.

Hier eine Langzeitmessung der Auslastung der CPU, 'Low' ist die freie Zeit, 'High' die Abarbeitungszeit des Interrutps. Da nur in jedem 5. Interrupt die AGC gerechnet wird, sind die Ausführungszeiten recht unterschiedlich und zeigen auch, dass bei der AGC noch Optimierungspotential besteht, denn hier gibt es eigentlich nicht so viel zu tun.



Wenn man in C oder C++ mit 'float' arbeitet, gibt es noch ein paar zu beachtende Fallstricke, die zwar keinen falschen, aber sehr ineffizienten Code erzeugen. In C und C++ ist nämlich der Standard-Typ 'double' und nicht 'float', und mit 'double' kann der Prozessor nichts anfangen, daher muss dieser mit Software emuliert werden, was sehr langsam ist. Auch wenn man nirgends 'double' schreibt, gibt es diesen Datentyp, wenn man nicht aufpasst, z.B. bei Konstanten oder Library-Aufrufen, hier zwei Beispiele:

float x, y;
x= y * 4.7;

Die Konstante 4.7 ist vom Typ 'double', weil das in C so definiert ist, was zur Folge hat, dass y in 'double' konvertiert wird, eine 'double'-Multiplikation ausgeführt und das Resultat nach 'float' konvertiert wird. Nicht ganz das, was man wollte. Richtig ist:

x = y * 4.7f;

Durch das 'f' hinter der Konstanten (ohne Abstand) wird dem Compiler mitgeteilt, dass die Konstante vom Typ 'float' sein soll, und dann wird es sehr effizient.

Library-Aufrufe, z.B. Wurzel:

x = sqrt(y);

Die Standard-Funktionen von 'math.h' haben alle den Typ 'double' und sind daher ineffizient. Es gibt aber von allen Funktionen eine 'float'-Variante, welche am Namensende ein 'f' hat, hier also 'sqrtf':

x = sqrtf(y)

Nach diesen Codier-Tips noch die Beschreibung der neuen Funktionen. Zuerst zum SSB-Demodulator. Hier wird das I- und Q-Signal mit einem Lokaloszillator gemischt, die Funktion ist dieselbe wie beim klassischen BFO. Damit nur ein Seitenband durchkommt, wird das I- und das Q-Signal mit um 90° phasenverschobenen Oszillatorsignalen gemischt und danach für USB addiert und für LSB subtrahiert. So wird das falsche Seitenband unterdrückt. Hier die Funktion als C-Code:

USB = I * cos(2*pi*f*t) + Q * sin(2*pi*f*t)
LSB = I * cos(2*pi*f*t) - Q * sin(2*pi*f*t)

Die Frequenz f ist dabei 300Hz grösser als die Eckfrequenz der ZF-Tiefpässe gewählt, so dass im NF-Signal die Frequenzen unterhalb 300Hz weggefiltert werden. Das erhöht einerseits die Verständlichkeit (SSB wird ja nur für Sprache verwendet) und zum anderen ergibt sich eine bessere Unterdrückung der Nachbarsignale, weil die Bandbreite reduziert werden kann.

Für Synchron-AM wird das Q-Signal mit einem einfachen PI-Regler auf Null geregelt, dabei wird das Ausgangssignal vom Regler als Offset zur Frequenz des numerischen Oszillators vom IQ-Mischer addiert, also eine klassische PLL. Damit bei fehlender Synchronisation der Integrator des Reglers nicht beliebig weit weglaufen kann, wird er auf +/-3kHz begrenzt, was bedeutet, dass der Haltebereich der PLL auf diesen Bereich beschränkt ist. Da der Regler langsam eingestellt ist, um bei Trägerschwund keine Störungen zu produzieren, ist der Fangbereich nicht allzu gross und er braucht etwas Zeit zum Einrasten. Hier gibt es noch Verbesserungspotential durch variable Regelparameter je nach Situation. Das NF-Signal ist dabei das I-Signal.

Als Nächstes kommt ein Inkrementalgeber für die Abstimmung und ein paar Zusatzmenus für Einstellungen, weiter ist noch ein EEPROM geplant, wo die Einstellungen gespeichert werden, damit sie beim Ausschalten nicht verlorengehen.

Gruss HB9

Zuletzt bearbeitet am 05.11.17 20:34

Datei-Anhänge
Auslastung.PNG Auslastung.PNG (6x)

Mime-Type: image/png, 8 kB

ADC_Interrupt_asm.s.txt ADC_Interrupt_asm.s.txt (9x)

Mime-Type: text/plain, 14 kB

ADC_Interrupt.cpp.txt ADC_Interrupt.cpp.txt (11x)

Mime-Type: text/plain, 10 kB

CPU_init.cpp.txt CPU_init.cpp.txt (9x)

Mime-Type: text/plain, 6 kB

main.cpp.txt main.cpp.txt (9x)

Mime-Type: text/plain, 2 kB

menu.cpp.txt menu.cpp.txt (9x)

Mime-Type: text/plain, 17 kB

05.11.17 20:15
HB9 

WGF-Premiumnutzer

05.11.17 20:15
HB9 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo zusammen,

hier noch das ergänzte Blockschema:



Im dezimierten Teil (gelb) wird übrigens praktisch alles Floating-Point gerechnet, da der Prozessor dies sehr gut kann und man so keine Sorgen mit Skalierungsfaktoren hat.

Wer es mit der SSB-Demodulation genauer wissen will, kann unter dem Begriff 'weaver ssb demodulator' gurgeln.

Hier noch die Beschreibung, wie ein numerischer Oszillator nach dem DDS-Prinzip funktioniert.
Die Grundfunktion ist einfach, hier der Pseudo-Code, der zyklisch mit der Samplingfrequenz fs aufgerufen wird:

Phase = Phase + Frequenz;
Signal = cos(Phase);

In der Praxis macht man sich zu Nutze, dass sich der cos nach 360° wiederholt und verwendet für die Phase Integer-Arithmetik. Dabei wird der Wertebereich von 'int' als Winkelbereich -180°..+180° aufgefasst, so hat man die Periode gratis. Da die Berechnung des cos im Allgemeinen zu lange dauert (ausser man hat einen 'richtigen' DSP und ausreichend Zeit), werden die Sinuswerte in einer Tabelle abgelegt. Damit diese Tabelle nicht zu gross wird, nutzt man nicht alle Bits von 'Phase', sondern nur die hochwertigen, rundet alsp den Winkel ab, dabei gilt es, das richtige Mass für ein ausreichend sauberes Signal und den Speicherbedarf der Tabelle zu finden. Im SDR wird eine Tabelle mit 4096 Einträgen verwendet, also die 12 hochwertigsten Bits von 'Phase' verwendet. In C sieht das dann so aus, wenn man davon ausgeht, dass 'int' 32 Bit gross ist:

int Frequenz;
unsigned int Phase;
const float Sinus[] = Sinuswerte -180..+180°, insgesamt 4096 Werte

float NCO(void)
{
Phase = Phase + Frequenz;
return Sinus[Phase >> 20]; // die 12 hochwertigsten der 32 Bits verwenden
}

Die Skalierung von 'Frequenz' ist einfach: Beim Wert 1 dauert es 2^32 Samplingperioden, bis 'Phase' eine ganze Periode gemacht hat, somit ist:

f = Frequenz * fs / 2^32 mit fs = Samplingfrequenz

Auch hier gilt natürlich das Sampling-Theorem, daher ist der maximal zulässige Wert für 'Frequenz' 2^31 - 1, also MAXINT. Bei höheren Werten gibt es Aliasing, die Frequenz sinkt wieder und ist 'negativ', das heisst, der Winkel 'Phase' wird bei jedem Durchgang kleiner statt grösser.

Bei einfacheren 8- oder 16-Bit-Prozessoren oder FPGAs wird häufig mit weniger als 32 Bit gerechnet, da die extrem feine Frequenzauflösung von 32 Bit meistens nicht benötigt wird und man so Ressourcen oder Rechenzeit sparen kann. Bei einem 32-Bit-Prozessor wie dem ARM (egal welcher Typ) spart man mit kleinerer Wortbreite aber nichts, daher wird beim SDR mit 32 Bit gerechnet.

Gruss HB9

Zuletzt bearbeitet am 05.11.17 20:18

Datei-Anhänge
Blockschema.png Blockschema.png (5x)

Mime-Type: image/png, 104 kB

05.11.17 20:47
joeberesf 

WGF-Premiumnutzer

05.11.17 20:47
joeberesf 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo HB9,

eijeijei!... da wird mir aber schon schwindelig. Sehr beeindruckend! Ich komme nun mit einer ganz simplen Frage, die mit SDR eigentlich überhaupt nichts gemein hat. Es geht um das oben gezeigte TFT- Touch. Du hast eine Display- Ausrichtung genutzt welche auch ich in meinem Morseprojekt nutze.




Ich kann zwar die einzelnen grafischen Elemente anordnen, aber die aktiven Touch- Schaltflächen drehen sich bei mir nicht mit. Wie funktioniert das? Bei mir funktioniert nur die Hochkant- Schaltflächen- Ausrichtung.

Gruß

Joerg

05.11.17 20:58
HB9 

WGF-Premiumnutzer

05.11.17 20:58
HB9 

WGF-Premiumnutzer

Re: Software Defined Radio

Hallo Joerg,

ich habe die Auswertung des Touch Screens selber geschrieben

Das mit den Bibliotheken ist immer so eine Sache, vermutlich ist bei deiner einfach vergessen gegangen, dass man die Koordinaten des Touch-Panels ebenfalls umrechnen muss, wenn man die Ausrichtung des Displays dreht. Eventuell findest du im Internet Hilfe, wenn du gezielt nach deinem Problem gurgelst, insbesondere die Angabe des Namens der Bibliothek und allenfalls des Displays ist hilfreich. Wenn alles schief geht, hilft nur noch, den Code zu analysieren und zu ändern, was je nach Kommentardichte und Programmierstil mühsam sein kann.

Gruss HB9

 1 2 3 4
 1 2 3 4
D-Wandler   Prozessor   einfach   Spiegelfrequenzunterdrückung   Mischer   Vorwärts-Schwundregelung   Floating-Point-Signalprozessoren   Display   Software   Übertragungsgeschwindigkeit   Morsedekodierungskästchen   Samples   Samplingfrequenz   Kommunikationsschnittstelle   Ausgangs-Samplingfrequenz   Initialisierungsfunktionen   zusammen   Defined   Bandbreite   Vorwärts-Verstärkungsfaktoren