Forum: Projekte & Code Arm Synthesizer mit LPC1114


von chris (Gast)


Angehängte Dateien:

Lesenswert?

Da es den LPC1114 im 28pol Dip Gehäuse gibt, finde ich diese MCU ideal, 
um einfach Synthesizer zu bauen.

Hier ein 5 Kanal DDS zur Erzeugung von Glockentönen:
http://www.hobby-roboter.de/forum/viewtopic.php?f=5&t=140

von chris (Gast)


Angehängte Dateien:

Lesenswert?

Hier gibt es eine Beispiel für das Programmieren des 28pol Dip mit einem 
LPC1114Xpresso:
http://www.sase.com.ar/2012/files/2012/10/Hands-on-NXP-Cortex-M0-LPC1114-en-package-DIP28.pdf

von Ale (Gast)


Lesenswert?

Ich habe gedacht daß der LPC1114 in DIL28 narrow war... ein .6" Gehäuse 
ist oldschool...

Schöne Projekt...

von Roland H. (batchman)


Lesenswert?

Ale schrieb:
> Ich habe gedacht daß der LPC1114 in DIL28 narrow war... ein .6" Gehäuse
> ist oldschool...

Weiß jemand, warum das so ist? Schon ein riesiges Ding. Richtig 
dramatisch ist es für meine Belange nicht, da der externe Quarz entfällt 
- der interne mit 48 MHz reicht mir.

von tft (Gast)


Lesenswert?

Woher kann ich diese dip 32 Beziehen als Student?
Mfg

von chris (Gast)


Lesenswert?


von Roland H. (batchman)


Lesenswert?

chris schrieb:
> Hier ein 5 Kanal DDS zur Erzeugung von Glockentönen

Habe es inzwischen ausprobiert, gefällt mir gut, Danke für den Source.

Kann es sein, dass die 2. Glocke wesentlich leiser als die erste ist?

> Da es den LPC1114 im 28pol Dip Gehäuse gibt, finde ich diese MCU ideal,
> um einfach Synthesizer zu bauen.

Bitte beachten, dass Pin 1.10 auf dem lpc1114 in DIP-28 nicht verfügbar 
ist. Der Source läuft m. E. so nicht auf dem lpc1114 in DIP-28.

Zum Source bzw. zur Materie hätte ich einen Haufen Fragen:

- Wo liegt denn ungefähr die untere Grenze (in MHz) für ein 5 Kanal DDS?
Und wie viele 5-DDS-Kanal Einheiten würde der lpc1114 bei 48 MHz, 
Sample-Frequenz 46875Hz, 10-Bit PWM verarbeiten können?

- Die fünf Kanäle entsprechen dem Wert von MAXPARTIAL? Und jeder der 
Kanäle trägt max. 1/5 zur Amplitude bei? Je mehr desto besser der Klang?

#
1
#define TIMEFAKTOR 11000
2
3
uint16_t time_bell_1[]={3000*2,3000*2,2376*2,2178*2,1980*2,1307*2}; // time in ms
4
5
Time_coefficient[n]=(int32_t)TIMEFAKTOR/time[n]*2;

Was ist der TIMEFAKTOR bzw. wie kommt man auf diesen Wert?

Stimmt der Kommentar mit den "time in ms"? Heisst dass, dass der 
Frequenzanteil schon die 6s vorhanden ist und nur durch den Envelope 
abgeschwächt wird? Wieso "mal 2"?

Wieso wird beim t-Koeff. nochmals mit zwei multipliziert?

#
1
outValue=temp+0x8000;

Wieso wird hier 0x8000 addiert?

#
1
uint16_t temp;
2
...
3
4
while(temp==MsTimer);
5
temp=MsTimer;

temp ist zunächst nicht definiert. Was machen die beiden letzten Zeilen? 
Verzögerung um eine ms?

#

Und zum Schluss: Wie kommt man überhaupt auf die Frequenz- und 
Zeitanteile?

Mit Dank im Voraus

von chris (Gast)


Lesenswert?

Hallo Roland,

es freut mich sehr, dass Du es ausprobiert hast :-)

>chris schrieb:
>> Hier ein 5 Kanal DDS zur Erzeugung von Glockentönen
>Habe es inzwischen ausprobiert, gefällt mir gut, Danke für den Source.
>Kann es sein, dass die 2. Glocke wesentlich leiser als die erste ist?

Eingentlich sollten die Glocken gleich laut sein. Meinem Gefühl nach 
klingt die zweite Glocke aber auch leiser. Das kann aber auch am 
Lautsprecher liegen. Die hohen Töne der ersten Glocke werden vielleicht 
von unserem Gehör als "lauter" wargenommen.

>> Da es den LPC1114 im 28pol Dip Gehäuse gibt, finde ich diese MCU ideal,
>> um einfach Synthesizer zu bauen.
>Bitte beachten, dass Pin 1.10 auf dem lpc1114 in DIP-28 nicht verfügbar
>ist. Der Source läuft m. E. so nicht auf dem lpc1114 in DIP-28.
Das habe ich nicht bedacht, da mein Test bis jetzt nur auf dem 
LPCXpresso gelaufen ist. Meine auf Ebay ersteigerten 28pol Dips sind 
leider noch nicht angekommen. Aber danke für den Tipp.

>Zum Source bzw. zur Materie hätte ich einen Haufen Fragen:
>- Wo liegt denn ungefähr die untere Grenze (in MHz) für ein 5 Kanal DDS?
>Und wie viele 5-DDS-Kanal Einheiten würde der lpc1114 bei 48 MHz,
>Sample-Frequenz 46875Hz, 10-Bit PWM verarbeiten können?

Ähm, die Frage verstehe ich nicht ganz. Mein LPCXpresso läuft mit 48MHz, 
also "Full Speed". Die Sample-Frequenz ergibt ist FS=48MHz/1024 (Stufen 
pro PWMPeriode ) =46875Hz
Man könnte die Prozessorfrequenz runter setzen, dann verschlechtert sich 
die Tonqualität etwas. Ich nehem an, dass die Glocken bei 16MHz 
Prozessorfrequenz noch gut klingen.
>- Die fünf Kanäle entsprechen dem Wert von MAXPARTIAL? Und jeder der
>Kanäle trägt max. 1/5 zur Amplitude bei? Je mehr desto besser der Klang?
Ja, die MAXPARTIAL sind die Anzahl der Sinusgeneratoren. Der Name kommt 
von den "Partialtönen" einer Glocke.

>#define TIMEFAKTOR 11000

>uint16_t time_bell_1[]={3000*2,3000*2,2376*2,2178*2,1980*2,1307*2}; // >time in 
ms

>Time_coefficient[n]=(int32_t)TIMEFAKTOR/time[n]*2;

>Was ist der TIMEFAKTOR bzw. wie kommt man auf diesen Wert?

Der TIMEFAKTOR ist ein "Relikt" aus einer früheren Implementierung der 
Glocken auf einem Atmega8. Im Array "time_bell" stehen die Abklingzeiten 
der einzelnen Partialtöne der Glocke. Ich muss gestehen, dass die 
Rechnung hier etwas unsauber und experimentell ist.

>Stimmt der Kommentar mit den "time in ms"? Heisst dass, dass der
>Frequenzanteil schon die 6s vorhanden ist und nur durch den Envelope
>abgeschwächt wird? Wieso "mal 2"?
Die Zeiten in "time_bell" sollen tatsächlich die Zeiten bis zum 
vollständigne Verstummen eines einzelnen Tons sein. Den Faktor 2 habe 
ich hineingeschrieben, weil es besser klang, wenn die Glocke schneller 
ausklingt und ich zu faul war, das ganze Array zu ändern.

>Wieso wird beim t-Koeff. nochmals mit zwei multipliziert?
dito

>outValue=temp+0x8000;
>Wieso wird hier 0x8000 addiert?
0x8000 ist der Gleichspannungswert. Da audioDAC1(uint16_t value) einen 
16Bit Gleichspannungswert benötigt.

>#
>uint16_t temp;
>...
>
>while(temp==MsTimer);
>temp=MsTimer;
>
>
>temp ist zunächst nicht definiert. Was machen die beiden letzten Zeilen?
>Verzögerung um eine ms?

Ja, in der main-Loop wird am Ende immer auf das Ablaufen einer 
Millisekunde gewartet. Dadurch weiss man, dass die Einhüllenden im 
Millisekundentakt erniedrigt werden können.

>#
>
>Und zum Schluss: Wie kommt man überhaupt auf die Frequenz- und
>Zeitanteile?
Ich hatte mich schon vor längerer Zeit mit der synthetischen Erzeugung 
von Glockentönen beschäftigt. In einem Buch über Glocken habe ich einige 
Tabellen zu den Partialtönen und den Abklingzeiten gefunden. Einige 
Informationen waren auch aus dem Internet.

Die Erzeugung von Glockentönen ist eigentlich relativ simple: Man 
benötigt einige Sinustöne, die unterschielich schnell ablklingen. Die 
typische Schwebung eines Glockentones ergibt sich aus zwei eng 
beieinaderliegenden Haupttönen.
Im Programm werden die Amplituden linear verringert. Relistischer wäre 
ein exponentieller Abfall was relativ einfach mit der Simulation eines 
RC-TP möglich wäre.

>Mit Dank im Voraus
Gerne.

Gruß,
chris

von chris (Gast)


Lesenswert?

Es ist ein großer Vorteil, die Sound-Routinen auf dem PC entwickeln und 
debuggen zu können. Deshalb habe ich das Programm so erweitert, dass man 
es für den PC oder das LPCXpresso1114 kompilieren kann.
Wird es für den PC kompiliert, werden zwei Datein als Output generiert:

- wav.raw ( int16 data )
- wav.dat ( ascii data )

Die raw-Datei kann man z.B. mittels Audacity abspielen.
Als Compiler habe ich GCC unter Eclipse CDT und Ubuntu verwendet. Es 
sollte sich aber auch auf Windows kompilieren lassen.

von chris (Gast)


Lesenswert?


von Lothar (Gast)


Lesenswert?

Ale schrieb:
> Ich habe gedacht daß der LPC1114 in DIL28 narrow war... ein .6" Gehäuse
> ist oldschool...

YouTube: A crazy way to convert a 600mil DIP to 300mil. [LPC1114]

von chris (Gast)


Lesenswert?

>YouTube: A crazy way to convert a 600mil DIP to 300mil. [LPC1114]

Irre ! Auf so eine Idee muss man erst mal kommen. Ich frage mich, was 
das auf diese Weise gefertigte Einzelstück kostet.
Wie er die Fräße benutzt finde ich beeindruckend. Das spricht für viel 
Erfahrung im Umgang mit der Technik. Auch das Vergießen am Schluss 
spricht für Professionalität.

von Roland H. (batchman)


Lesenswert?

chris schrieb:
> Ja, die MAXPARTIAL sind die Anzahl der Sinusgeneratoren. Der Name kommt
> von den "Partialtönen" einer Glocke.

D. h. der Klang wird mit 5 Sinusgeneratoren gebildet, und jeder ist für 
einen Partialton zuständig?

Bedeutet das im allg., dass die Anzahl der Generatoren und der 
Partialtöne bei DDS gleich ist?

Bei ring_bell() werden max. MAXPARTIAL Werte aus den Parametern 
übernommen.
In der Deklaration werden aber mehr als MAXPARTIAL Partialtöne definiert 
(und dann m. E. nicht verwendet?!).

Und noch eine Frage: Wenn man das Ausklingen nicht haben möchte, welchen 
(konstanten) Wert würde man anstelle von Envelope[n] verwenden?

von chris (Gast)


Lesenswert?

>D. h. der Klang wird mit 5 Sinusgeneratoren gebildet, und jeder ist für
>einen Partialton zuständig?
Ja, ein Partialton ist eine Schwingung, die von einem Sinusgenerator 
erzeugt wird.

>Bedeutet das im allg., dass die Anzahl der Generatoren und der
>Partialtöne bei DDS gleich ist?
Der Begriff DDS wird meistens für nur genau einen Oszillator verwendet.

>Bei ring_bell() werden max. MAXPARTIAL Werte aus den Parametern
>übernommen.
Vielleicht wäre es besser, ich würde MAXPARTIAL in NUMBER_OF_OSCILLATORS 
umbenennen.

>In der Deklaration werden aber mehr als MAXPARTIAL Partialtöne definiert
>(und dann m. E. nicht verwendet?!).

Die Rechenzeit des LPC1114 hat leider nur für 5 DDS-Oszillatoren 
ausgereicht. ( Optimierungsstufe des GCC: -O0 ). Ale ( post weiter oben 
) hat vorgeschlagen, die Compileroptimierung -O2 zu verwenden. Damit 
reicht die Rechenzeit für 10 Oszillatoren. Um so mehr Oszillatoren, umso 
genauer die Synthese des Glockentons.

>Und noch eine Frage: Wenn man das Ausklingen nicht haben möchte, welchen
>(konstanten) Wert würde man anstelle von Envelope[n] verwenden?

MAXLEVEL/MAXPARTIAL

von chris (Gast)


Angehängte Dateien:

Lesenswert?

Jetzt ist ein Sequencer, der diese MP3-änliche Kodierung versteht
http://code.google.com/p/arduino-playtune/
in die Simulation auf dem PC eingebunden. Ebenso eine Hüllkurve mit 
ATTACK,DECAY,SUSTAIN und RELEASE.
Bin mal gespannt, ob sich an der Tonqualität noch etwas drehen lässt ...

von chris (Gast)


Lesenswert?

Hallo Roland,

jetzt ist die neue Version mit Playtune Sequencer online.
Könntest Du sie bei Dir ausprobieren? Mich würde interssieren, ob alles 
problemlos läuft.

Gruß,
chris

von chris (Gast)


Lesenswert?

Will man einen neuen Mikrocontroller verwenden, ist das immer mit 
verschiedenen Schwierigkeiten verbunden: Die IDE ist ungewohnt, 
Registereinstellungen sind anders, Compiler finden die Pfade nicht usw.

Gerade eben hatte ich wieder einige dieser Umstiegschwierigkeiten: Für 
die bisherigen Experimente habe ich das LPCXpresso1114 und die dazu 
gehörige Entwicklungsumgebung von Code-Red verwendet ( 
http://www.code-red-tech.com/lpcxpresso.php )
Jetzt wollte ich den LPC1114FN28 im DIP Gehäuse verwenden. Also habe ich 
( wie hier Beitrag "Re: Arm Synthesizer mit LPC1114" gezeigt ) 
den Prozessor in der freudigen Erwartung verkabelt, sofort mein Programm 
darauf laufen lassen zu können. Aber weit gefehlt:

  03: Failed on chip setup
  Invalid, mismatched, or unknown part

Tja, wie sich herausstellt, muss für das DIP-Package eine andere 
MCU-Einstellung verwendet werden, da das DIP-Package eine andere 
Idendifikationsnummer benötigt. Also muss diese umgestellt werden:

Eclipse->Project->Properties->C/C++Build->MCU settings->LPC1114FN/102

Nur leider hatte meine Version der Code-Red-IDE diese MCU-Nummer nicht. 
Warum? Weil ich meine IDE vor einem Jahr installiert hatte und da war 
diese Nummer noch nicht vorhanden. Daher also:
- IDE deintallieren,
- 303MByte neue IDE herunterladen
- Installieren
- neuen Freuschaltungscode bei Code-Red holen.
zusätzlich noch:
- neue CMSIS ( 
http://ics.nxp.com/support/lpcxpresso/zip/CMSISv2p00_LPC11xx.zip )
- Code Samples für LPCXpresso1114 ( 
http://ics.nxp.com/support/documents/microcontrollers/zip/lpcxpresso.examples.lpc1114.301.zip 
)

Und siehe da, die IDE konnte sich mit der MCU verbinden. Lief das 
Programm? Nein. ( war ja klar )

Also: Unterschiede zum LPC-Expresso feststellen. Erstens: das LPCXpresso 
hat einen Quarz. Aha !
Also rausfinden, wo der Systemclock vom internen Oscillator auf den 
externen Quarz umgeschalten werden kann. Gefunden habe ich die 
Einstellungen in der Konfiguration des Projekts für die CMSIS in Eclipse 
"config/system_LPC11xx.h".

Dort habe ich folgende Veränderung vorgenommen:
1
//#define SYSPLL_SETUP          1
2
// don't use PLL 17.2.2013 ch
3
#define SYSPLL_SETUP          0
4
5
#define SYSPLLCTRL_Val        0x00000023
6
//#define MAINCLKSEL_Val        0x00000003
7
// use internal RC oscillator ( IRC) modified 17.2.2013 ch
8
#define MAINCLKSEL_Val        0x00000000

Das Ergenis: Hurra! Das Blink Programm blinkt.

Aber: Ein wenig muss man ja experimentieren. Da frage ich mich für was 
ist eigentlich MAINCLKSEL? Also flux MAINCLKSEL_Val wieder auf den alten 
Wert 03 zurückgestellt. Ergebnis: Prozessor abgeschossen. Es scheint 
also wie beim Atmega zu sein: stellt man die Clk-Source falsch ein, geht 
nichts mehr.

Macht aber nichts, ich habe ja noch 3 Bausteine in Reserve und es freut 
mich, dass ich einen Weg gefunden habe, das Blink-Programm laufen zu 
lassen.

Jetzt muss ich in den Synthesizer Sourcen noch die Ports umstellen, da 
ja wie Roland weiter oben darauf hingewiesen hat, das DIP-Package nicht 
alle Ports des TSSOP hat und ich ausgerechnet die nicht vorhandenen 
PWM-Pin auf einen diese Pins gelegt habe ...

von chris (Gast)


Lesenswert?

praktisch: das Pinout des LPC1114FN28

http://www.joaov.com/lpc1114/

von chris (Gast)


Lesenswert?

Mit der obigen Einstellung läuft die MCU nur mit 12MHz. Für den 
Synthesizer wird aber die volle Rechenleistung mit 48MHz benötigt.

Die Einstellungen sehen dann wie folgt aus:
1
//#define SYSPLLCLKSEL_Val    0x00000001 // crystal system oscillator
2
#define SYSPLLCLKSEL_Val      0x00000000 // IRC oscillator
3
#define SYSPLL_SETUP          1          // use PLL
4
//#define SYSPLL_SETUP        0          // don't use PLL 
5
#define MAINCLKSEL_Val        0x00000003 // use PLL out as system clk
6
//#define MAINCLKSEL_Val      0x00000000 // use IRC oscillator as system clk
7
#define SYSPLLCTRL_Val        0x00000023 // Feedback divider value, Post divider ratio P.

von chris (Gast)


Angehängte Dateien:

Lesenswert?

Hier ein Bildchen des Versuchsaufbaus ( leider etwas unscharf, da ich im 
Moment nur die Webcam des Rechners habe )

von chris (Gast)


Lesenswert?

Wer die Beitrag "Re: Klingel mit 100 Melodien - last minute Weihnachtsgeschenk" auf dem Arm 
ausprobieren möchte, kann den Sequencer anpassen:
1
//#define USE_PLAYTUNE
2
//#define USE_SIMPLE_TEST_SEQUENCER
3
#define KLINGEL
4
5
....
6
7
#ifdef KLINGEL
8
  static uint32_t liedIndex=0,endIndex=0;
9
  static uint32_t waitTime=100;
10
  static uint8_t laenge,hoehe,speed;
11
  static uint8_t liedNr=0;
12
13
  if(MsTimer>=waitTime)
14
  {
15
    if(liedIndex==endIndex) // load new sound
16
    {
17
      liedIndex=liedofs[liedNr];
18
      speed=lied[liedIndex++];
19
      endIndex=liedofs[liedNr+1];
20
      liedNr++;
21
      //noteOff(0,hoehe); // turn off old note
22
      voiceOff();
23
      waitTime=2000; // wait befor playing
24
    }else // play note
25
    {
26
      laenge=lied[liedIndex]>>5;
27
      waitTime=zeit[laenge]*20*speed;
28
      //noteOff(0,hoehe);
29
      hoehe=(lied[liedIndex]&0x1F)+60-12; // midi note 60= pitch C4, 12 notes/octave
30
      organ(note2frequency(hoehe)); // wir nehmen die Orgel-Simualtion
31
      //noteOn(0,hoehe,100);
32
      liedIndex++;
33
    }
34
    MsTimer=0;
35
  }
36
#endif

Jetzt noch "lied.h" aus Beitrag "Klingel mit 100 Melodien - last minute Weihnachtsgeschenk" 
laden und die Array-Definitionen etwas anpassen. D.h. die AVR 
spezifischen Dinke wie PROGMEM weglassen und "const" vor die Arrays 
schreiben, damit die Daten doppelt noch im RAM gehalten werden ( was mit 
seinen 4KB sowieso dafür nicht reicht ).

Beispiel:
1
const uint8_t lied []  = {
2
3
1 //Lied Nr. 1 Offset:0
4
5
,0,136,128,107,128,72,64,72,141,136,134,136,128,111,128,72,64,72,144,143,139,136,143,148,72,70,64,70,131,139,200,200,192,82,143,141,139,200,171,72,64,72,141,136,134,200,175,72,64,72,144,143,139,136,143,148,72,70,64,70,131,139,200,200
6
7
,2 //Lied Nr. 2 Offset:65
8
9
....

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.