Hallo Leute, folgendes Problem: ich habe einen Sinus mit DDS erstellt und je nach Veränderung des IR1-Wertes ändert sich die Frequenz. Leider ist bei 400 HZ Schluss - Wenn ich den IR1 noch kleiner setze, ändert sich der Sinus nicht mehr, habe es mit einem Oszilloskop nachgemessen. Hat jemand eine Idee, woran das liegt? Gruß, Martin
Martin schrieb: > Hat jemand eine Idee, woran das liegt? Klar: du mußt den Increment in Zeile 42 ändern. Auf Deutsch: woher soll denn irgendwer irgendwas wissen? Keiner kennt deine Hardware oder dein Programm.
Wir haben zufaelligerweise genau dieselbe Schaltung vor uns liegen und erreichen aber 650Hz. Waere das genuegend ?
Hi >Leider ist bei 400 HZ Schluss - Wenn ich den IR1 noch kleiner setze, >ändert sich der Sinus nicht mehr, habe es mit einem Oszilloskop >nachgemessen. Dann hast du etwas falsch gemacht. MfG Spess
Hier ist mein Quelltextauszug:
1 | #include <avr/io.h> |
2 | #include <avr/interrupt.h> |
3 | #include <stdio.h> |
4 | #include "D:\lcd.h" |
5 | |
6 | const uint8_t sinustabelle[256] = //HexaWerte = 8 Bit; Anzahl der Tabellenwerte:256 |
7 | {
|
8 | 0x80,0x83,0x86,0x89,0x8C,0x8F,0x92,0x95, |
9 | 0x98,0x9C,0x9F,0xA2,0xA5,0xA8,0xAB,0xAE, |
10 | 0xB0,0xB3,0xB6,0xB9,0xBC,0xBF,0xC1,0xC4, |
11 | 0xC7,0xC9,0xCC,0xCE,0xD1,0xD3,0xD5,0xD8, |
12 | 0xDA,0xDC,0xDE,0xE0,0xE2,0xE4,0xE6,0xE8, |
13 | 0xEA,0xEC,0xED,0xEF,0xF0,0xF2,0xF3,0xF5, |
14 | 0xF6,0xF7,0xF8,0xF9,0xFA,0xFB,0xFC,0xFC, |
15 | 0xFD,0xFE,0xFE,0xFF,0xFF,0xFF,0xFF,0xFF, |
16 | 0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFE,0xFE, |
17 | 0xFD,0xFC,0xFC,0xFB,0xFA,0xF9,0xF8,0xF7, |
18 | 0xF6,0xF5,0xF3,0xF2,0xF0,0xEF,0xED,0xEC, |
19 | 0xEA,0xE8,0xE6,0xE4,0xE2,0xE0,0xDE,0xDC, |
20 | 0xDA,0xD8,0xD5,0xD3,0xD1,0xCE,0xCC,0xC9, |
21 | 0xC7,0xC4,0xC1,0xBF,0xBC,0xB9,0xB6,0xB3, |
22 | 0xB0,0xAE,0xAB,0xA8,0xA5,0xA2,0x9F,0x9C, |
23 | 0x98,0x95,0x92,0x8F,0x8C,0x89,0x86,0x83, |
24 | 0x80,0x7C,0x79,0x76,0x73,0x70,0x6D,0x6A, |
25 | 0x67,0x63,0x60,0x5D,0x5A,0x57,0x54,0x51, |
26 | 0x4F,0x4C,0x49,0x46,0x43,0x40,0x3E,0x3B, |
27 | 0x38,0x36,0x33,0x31,0x2E,0x2C,0x2A,0x27, |
28 | 0x25,0x23,0x21,0x1F,0x1D,0x1B,0x19,0x17, |
29 | 0x15,0x13,0x12,0x10,0x0F,0x0D,0x0C,0x0A, |
30 | 0x09,0x08,0x07,0x06,0x05,0x04,0x03,0x03, |
31 | 0x02,0x01,0x01,0x00,0x00,0x00,0x00,0x00, |
32 | 0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x01, |
33 | 0x02,0x03,0x03,0x04,0x05,0x06,0x07,0x08, |
34 | 0x09,0x0A,0x0C,0x0D,0x0F,0x10,0x12,0x13, |
35 | 0x15,0x17,0x19,0x1B,0x1D,0x1F,0x21,0x23, |
36 | 0x25,0x27,0x2A,0x2C,0x2E,0x31,0x33,0x36, |
37 | 0x38,0x3B,0x3E,0x40,0x43,0x46,0x49,0x4C, |
38 | 0x4F,0x51,0x54,0x57,0x5A,0x5D,0x60,0x63, |
39 | 0x67,0x6A,0x6D,0x70,0x73,0x76,0x79,0x7C, |
40 | };
|
41 | |
42 | void initialisierung() |
43 | {
|
44 | ICR1=0x3E8; //1000 als Hexazahl (Bis wohin gezählt wird); Je kleiner, desto höher die Frequenz |
45 | |
46 | |
47 | TCCR1A=(1<<WGM11); |
48 | TCCR1B=(1<<WGM13) | (1<<WGM12) | (1<<CS10) ; |
49 | //WGM : Fast PWM mit ICR1-Wert; Fast PWM: Zähler geht auf Null, sobald ICR1 erreicht wird.
|
50 | TIMSK=(1<<TICIE1); // Interrupt wird ausgelöst, wenn ICR1 erreicht wird; Löst Timer_CAPT_vect aus. |
51 | |
52 | }
|
53 | |
54 | ISR(TIMER1_CAPT_vect) //Timer-Interrupt-Routine, wird ausgelöst, wenn ICR1 erreicht wird. |
55 | {
|
56 | static uint8_t sinus_zaehler=0; //Gibt an, welche Position im Sinus ausgegeben wird. |
57 | |
58 | PORTC &=~(0x0F); //C0 - C3 werden auf 0 gesetzt. |
59 | PORTC |= (sinustabelle[sinus_zaehler])&(0x0F); //Wert sinus_zaehler in sinustabelle mit der Maske 0x0F und-verknüpft, |
60 | //damit nur die Werte C0-C3 verwendet werden.
|
61 | |
62 | PORTB &=~(0x3C); //B2 - B5 werden auf 0 gesetzt. |
63 | PORTB |= (sinustabelle[sinus_zaehler]>>2)&(0x3C);//Wert sinus_zaehler in sinustabelle wird um zwei Stellen nach rechts verschoben, |
64 | //und anschließend mit der Maske 0x3C und-verknüpft,
|
65 | //damit nur die Werte B2-B5 verwendet werden.
|
66 | |
67 | sinus_zaehler++; //Inkrementierung der Sinus-Position |
68 | }
|
69 | |
70 | |
71 | int main(void) |
72 | |
73 | {
|
74 | char run=1; |
75 | |
76 | DDRC= (1<<PINC0) | (1<<PINC1) | (1<<PINC2) | (1<<PINC3); |
77 | DDRB= (1<<PINB2) | (1<<PINB3) | (1<<PINB4) | (1<<PINB5); |
78 | DDRD= (1<<PIND3); |
79 | |
80 | PORTD |= (1<<PIND3); // Stromversorgung für Operationsverstärker |
81 | |
82 | initialisierung(); //Aufruf der Funktion "initialisierung" |
83 | |
84 | |
85 | |
86 | sei(); // Globale Interrupts aktivieren |
87 | |
88 | while(run) // Endlosschleife |
89 | {
|
90 | }
|
91 | |
92 | }
|
Den Sinus erzeuge ich mit je 4 Pins von Port B % C.
Hi Mach dich erst mal über DDS schlau: http://www.analog.com/static/imported-files/tutorials/MT-085.pdf http://www.analog.com/static/imported-files/tutorials/450968421DDS_Tutorial_rev12-2-99.pdf MfG Spess
Ich habe dieses Problem auch. Bei mir war allerdings schon bei ~110Hz Schluss. Ich hatte damals ~ 190 Werte in meiner Tabelle. Ich habe um höhere Frequenzen zu erreichen einfach weniger Werte genommen. Wenn man mal überlegt, liegt die Interrptfrequenz bei 100 Werten mal 200Hz schon bei 20kHz(!). Das is ne Menge. Ich habe einen Mega128 @ 16MHz verwendet. Heute würde ich einen XMega vorziehen, der dürfte dank DMA schneller sein. Es liegt also daran, dass der AVR zu langsam ist, bzw. du nicht mehr Werte in dieser Zeit ausgeben kannst. Ist also ein Problem mit der Rechenleistung! Sollte ich mit meiner Vermutung falsch liegen, wäre ich auch an einer Lösung interessiert. Gruß Knut
Ich habe die Werte damals über PWM + Filter ausgegeben, klappte super! Aber R2R geht ebensogut! Knut
Also ich versteh den Code zwar nicht ohne stundenlanges Nachdenken, aber ich rate mal dass Du die Tabelle Wert für Wert ausliest mit unterschiedlichen Geschwindigkeiten. Das sagt mir dass Du noch nie vom Abtasttheorem gehört hast. Du kannst in der Tabelle Werte überspringen, das gibt dann immer noch einen Sinus. Nach oben Schluss ist dann wenn Du pro Sinusperiode nur noch 2 Stützpunkte hast. Andererseits: was Du da machst ist zwar ein digital erzeugter Sinus, aber nicht DDS. DDS nimmt einen schnellen Sinus, haut den auf nen schnellen DAC, dann wird das ganze noch etwas tiefpassgefiltert, und fertig. Eine PWM im Signalpfad zu haben (als Ersatz für einen schnellen DAC) bremst alles um den Faktor 100 runter. Macht irgendwie keinen Sinn. Meine Empfehlung: Bau Dir einen 2. Ordnung digitalen Delta Sigma Modulator, füttere ihn mit einem 8bit Sinus, der Delta Sigma macht daraus 4bit, und mit den 4bit gehst Du auf einen externen R2R DAC plus Tiefpassfilter. Der DAC arbeitet dann mit 2MHz, und DU kommst locker mit Deinem Sinus auf 100-200kHz. Noch Fragen?
Martin1 schrieb: > DDS nimmt einen schnellen Sinus Was unterscheidet denn einen schnellen Sinus von einem langsamen Sinus??? Doch eigentlich nur die Periodendauer. Die ist abhängig, wie schnell die Werte ausgelesen werden. > Eine PWM im Signalpfad zu haben (als Ersatz für einen schnellen > DAC) bremst alles um den Faktor 100 runter. Kannst du das näher Erleutern? Gruß Knut
@Martin DDS geht so: Du definierst einen Phasenakkumulator mit z. B. 16bit. Du setzt die Interruptrate mittels Timer auf z. B. 65536Hz. Es ginge natürlich auch jede andere Frequenz, aber damit bekommst du so schön 1Hz Auflösung. Die oberen 8bit deines Akkumulators nimmst du zum Adressieren der Sinustabelle. Auflösung: 65536Hz/65536 = 1Hz Die 65536 ist deine Akkumulatorgröße. Wenn du jetzt 10Hz haben willst, dann addierst du jedesmal 10 zum Akkumulator. freq=10 phase=0 ISR: phase = phase+freq Mit den oberen 8 bits vom Accu addressierst du deine Sinustabelle. ISR Ende Wenn du 100Hz haben willst, dann einfach freq=100 Am Ausgang der DDS brauchst du in Hardware ein Filter höheren Grades.
@Knut Ein langsamer Sinus ist einer dessen sämtliche Oberwellen durch das nachgeschaltete Tiefpassfilter rutschen. Bei einem 4bit R2R DAC generierten Sinus sollte man die Oberwellen wohl besser wegfiltern, das klappt schlecht wenn der Sinus zu niederfrequent ist.
Hallo, Ich habe folgenden DDS Generator nach gebaut.Habe mir ein 25khz sinus generiert. http://www.scienceprog.com/avr-dds-signal-generator-v20/ kann mir einer erklären was genau das Widerstandsnetzwerk am Ausgang macht. Ich weiss zwar das eine Digital analog wandlung ist, aber wie genau funktioniert das.
Erklärungen: http://www.mikrocontroller.net/articles/DDS http://www.mikrocontroller.net/articles/DA-Wandler MFG:MBP
Martin1 schrieb: > Ein langsamer Sinus ist einer dessen sämtliche Oberwellen durch das > nachgeschaltete Tiefpassfilter rutschen. Ein Sinus hat keine Oberwellen. Du mußt nur alles oberhalb fs/2 wegfiltern. Die Störungen, die Du aufgrund fehlender Spannungsauflösung hast, sind keine Oberwellen. Wenn Du die beseitigen möchtest, solltest Du über ein 16-Bit-System nachdenken. Mit einem ATmega168 schafft man im übrigen bis zu 500kHz Signalfrequenz bei 8 Bit Auflösung. Ach ja: Du solltest unbedingt dafür sorgen, das alle Bits gleichzeitig am DA-Wandler ankommen. Gruß Jobst
Ja meine Ich ja einen DA - Wandler. Anstatt das Widerstandsnetzwerk zu benutzen, kann doch bestimmt DA-Wandler ICs benutzen oder ?
DA-Wandler-ICs sind zur DA-Wandlung gänzlich ungeeignet. Deshalb heißen die so. Gruß Jobst
Die D/A-Wandler ICs sind natürlich viel genauer als sowas selbst gebautest. Allerdings kosten schnelle D/A-Wandler dann auch etwas mehr als dein Mikroprozessor.
peter schrieb: > Ja meine Ich ja einen DA - Wandler. > Anstatt das Widerstandsnetzwerk zu benutzen, kann doch bestimmt > DA-Wandler ICs benutzen oder ? Hallo Peter, Das ist eine Frage des Typs des DA-Wandlers; Die Auflöung ist wohl weniger bedeutend als die Geschwindigkeit, wenn es ein Funktionsgenerator werden soll. Geschwindikeit: Insbesondere die, in welcher die Digital-Daten an den Wandler kommen. Ein 8 Bit R2R-DAC dierekt am µc ist einfach und sehr schnell anzusteuern: Ein Byte 1:1 an den Port und der neue Analogwert pendelt sich sogleich ein. Mit SPI oder TWI (I2C) musst Du ersteinmal serielle Kommunokation vorbereiten und ablaufen lassen, ehe die Daten zu analog umgesetzt werden. TWI ist im übrigen meist noch langsamer als SPI. Wenn Du allerdings nur NF-Audio erzeugen möchtest, so kann ich mir vorstellen, dass Du sogar mit einem TWI-Typ noch zu einem Ergebniss kommst. MFG:MBP Markus.
peter schrieb: > Anstatt das Widerstandsnetzwerk zu benutzen, kann doch bestimmt > DA-Wandler ICs benutzen oder ? Wenn du hohe Frequenze erzeugen willst, verringserst du durch zusätzlich Zeit, die du brauchst, um die Daten zum DAC zu übertragen, deine obere Grenzfrequenz. Probier mal den miniDDS von Jesper mit 8-Bit R2R DA-Wandler (bis 200..300 kHz je nach Quarz, Zykluszeit 9 Take auf ATmega8) http://www.myplace.nu/avr/minidds/index.htm
Michael schrieb: > peter schrieb: >> Anstatt das Widerstandsnetzwerk zu benutzen, kann doch bestimmt >> DA-Wandler ICs benutzen oder ? > > Wenn du hohe Frequenze erzeugen willst, verringserst du durch zusätzlich > Zeit, die du brauchst, um die Daten zum DAC zu übertragen, deine obere > Grenzfrequenz. > > Probier mal den miniDDS von Jesper mit 8-Bit R2R DA-Wandler (bis > 200..300 kHz je nach Quarz, Zykluszeit 9 Take auf ATmega8) > http://www.myplace.nu/avr/minidds/index.htm Hab mit Hilfe von Jesper das folgende gebaut: http://www.elo-web.de/f-drabek Habe absichtlich eine höhere Zykluszeit gewählt. Warum steht im Artikel.
Rudi D. schrieb: > http://www.elo-web.de/f-drabek 'Die modernste Art von RC-Generatoren ist zweifellos die Synthese mit einem digitalen Signalprozessor.' ... ist dann nur kein RC-Generator mehr ... Rudi D. schrieb: > Warum steht im Artikel. Und Du erwartest nun, daß die Leute Deinen Artikel kaufen? Gruß Jobst
S. T. schrieb: > es soll auch parallel angesteuerte DACs geben DAC080x z.B. http://www.reichelt.de/ICs-CA-ISD-/DAC-0808-LCN/index.html?;ARTICLE=7027 oder PCM54 ;-) Gruß Jobst
Jobst M. schrieb: > Rudi D. schrieb: >> http://www.elo-web.de/f-drabek > > 'Die modernste Art von RC-Generatoren ist zweifellos die Synthese mit > einem digitalen Signalprozessor.' > > ... ist dann nur kein RC-Generator mehr ... > > > Rudi D. schrieb: >> Warum steht im Artikel. > > Und Du erwartest nun, daß die Leute Deinen Artikel kaufen? > > > Gruß > > Jobst Der Artikel kostet natürlich nichts. Er ist auch noch bei elektronik-labor.de gelistet.
Rudi D. schrieb: > Der Artikel kostet natürlich nichts. > Er ist auch noch bei elektronik-labor.de gelistet. aber dort gut versteckt... --> Alle Artikel im Überblick. --> 17.11.10: AVR-Controller: DDS-Generator MFG:MBP
Markus B. p. schrieb: > --> 17.11.10: AVR-Controller: DDS-Generator http://elektronik-labor.de/AVR/DDSGenerator.htm Gruß Jobst
Jobst M. schrieb: > Markus B. p. schrieb: >> --> 17.11.10: AVR-Controller: DDS-Generator > > http://elektronik-labor.de/AVR/DDSGenerator.htm > > > Gruß > > Jobst Hallo Jobst, da ich mir nicht durchgelesen habe, ob der Seitenbetreiber direkte Links auf Unterseiten möchte oder nicht, daher habe ich nur eine "Wegbeschreibung" geliefert. MFG:MBP
Markus B. p. schrieb: > ob der Seitenbetreiber direkte Links auf Unterseiten möchte Ich habe nichts gegenteiliges gefunden ... Gruß Jobst
mbp schrieb:
> Ein 8 Bit R2R-DAC dierekt am µc ist einfach und sehr schnell
anzusteuern:
Ein Byte 1:1 an den Port und der neue Analogwert pendelt sich sogleich
ein
Kann jemand den Typ eines solchen R2R-DAC sagen?
Simon K. schrieb: > peter schrieb: >> Kann jemand den Typ eines solchen R2R-DAC sagen? > > Meinst du das jetzt ernst? Vielleicht ist ja auch Google kaputt? Edit: nein, habs grad probiert. Google geht noch.
R2R-DAC habe ich natürlich schon gefunden. aber ich hätte gerne einen den man wie erwähnt 1:1 an das Port anschließen kann.
Da gab es mal die ZN42x-Familie. Teilweise noch erhältlich? Hier z.B. 8-Bit DA ohne Latch: http://pdf1.alldatasheet.com/datasheet-pdf/view/83179/ETC/ZN429.html hans
peter schrieb: > R2R-DAC habe ich natürlich schon gefunden. aber ich hätte gerne einen > den man wie erwähnt 1:1 an das Port anschließen kann. Warum schaust du dir nicht die Lösung von mir an ? Du brauchst nur eng tolerierte Widerstände und sonst nichts.
peter schrieb: > Kann jemand den Typ eines solchen R2R-DAC sagen? Ich weiß zwar nicht, ob es nun ein R2R oder ein DAC mit gewichteten Widerständen ist, für die Anwendung ist das aber auch egal. Auf jeden Fall habe ich viel weiter oben schon einen genannt - sogar mit Link ... Wozu antwortet man eigentlich?
Hier wär mal ein 8bit-DAC der nur +5V Versorgung braucht. Den gibts übrigens bei Reichelt. http://www.analog.com/static/imported-files/Data_Sheets/AD557.pdf
HI CSD hat auch reine R2R-Widerstandsnetzwerke. MfG Spess
spess53 schrieb: > > CSD hat auch reine R2R-Widerstandsnetzwerke. Das 1k Netzwerk ist zwar billig aber nicht so gut geeignet für direkte Anschaltung an Ports. Die 10k Variante kann man IMHO mit genauen Widerständen aus der Schatzkiste billiger herstellen. Wenn man die nicht hat, dann das 10k Netzwerk kaufen, denke ich. Oder Widerstände ausmessen, was ja immer geht.
Hallo, ich habe mir jetzt eien DAC 0808LCN besorgt. http://www.datasheetcatalog.org/datasheet2/8/0iff6chuycj3uriy0x2ls8p5cwfy.pdf nur weiss ich jetzt genau wie ich den anschließen muss. Digital in Inputs müsste ich ja 1:1 an mein PORTA anschließen können(PA0 -> A1,PA1 -> A2, usw.). Nur was ist mit VCC,Vref+,Vref- und VEE ich weis, dass es schon mehrere Beiträge zu diesem Thema gibt. Aber eine Antwort konnte ich daraus nicht gewinnen. Wäre nett wenn ihr mir nochmal weiterhelfen könntet. Gruß Peter
peter schrieb: > Nur was ist mit VCC,Vref+,Vref- und VEE Datenblatt: Seite 4 Typical Application MFG:MBP
Schaltbild Figure1 http://www.datasheetcatalog.org/datasheet/nationalsemiconductor/DS005687.PDF Der DAC0808 braucht -15V. Wenn du die nicht hast, vergiss ihn
habe jetzt die schaltung nach figure 9 aufgebaut. nur das ich Vs weglassen habe. ich will ja ein 22khz sinussignal erzeugen, nur ausgang ausgang bekomme jetzt 3MHZ sinussignal. habe ich irgendwie ein Frequenzbeschleuniger gebaut? weiß jemand woran das liegen könnte?
Ich verstehe ja nicht, warum du nicht aus Widerständen ein R2R Netzwerk an einem Port anhängst. Da kann nichts passieren. Es ist einfach nur passiv.
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.