Basierend auf Ihren Kommentaren, verwenden Sie ~ 12MHz Uhr als Eingang für Ihren Timer, und von Ihrem Code, verwenden Sie 8-Bit-Timer 0 im CTC-Modus mit OCR0A als Ihr Top. Sie haben OC0A gesetzt, um bei einer Vergleichsübereinstimmung zu schalten.
Nach der 2560 Datenblatt wird die Frequenz Ihrer Timer gegeben durch:
F_CLK/(2 * (1 + OCR0A)) | F_CLK ~ = 12MHz
Dies ist ein 8-Bit-Zeitgeber, so dass bedeutet, dass die Mindestfrequenz, die Ihre PWM durch gegeben erzeugen:
12e6/(2 * (1 + 255)) ~ = 20KHz
Sie können mit dieser Konfiguration einfach keinen Signalton erzeugen, es sei denn, Sie verlangsamen die Uhr, die Sie für Ihren Timer verwenden oder verwenden einen Timer, der höher zählen kann.
1) Verwenden Sie einen 16-Bit-Zähler (d. H. Timer1). Das wird Ihnen eine Mindestfrequenz von ~ 90Hz geben und eine maximale Frequenz von ~ 6 MHz, die Ihnen viel Bereich geben sollte Töne erzeugen:
/* WGM BITS = 0100: CTC Mode */
/* COMA BITS = 01: Toggle OC1A on compare match */
/* CS BITS = 111: External clock source on rising edge */
TCCR1A = (0 << COM1A1) | (1 << COM1A0) | (0 << WGM01) | (0 << WGM00);
TCCR1B = (1 << WGM12) | (1 << WGM13) | (1 << CS02) | (1 << CS01) | (1 << CS00);
2) Verwenden Sie die interne Taktquelle als Zeituhr anstelle eines externe Quelle. Wenn Sie die Sicherungsbits nicht geändert haben oder Sie sie irgendwo im Code ändern, beträgt die Taktfrequenz 1 MHz. Das Vorskalieren der Uhr um 8 ergibt einen Frequenzbereich von ~ 250 Hz - ~ 60 kHz.
/* WGM BITS = 010: CTC Mode */
/* COMA BITS = 01: Toggle OC1A on compare match */
/* CS BITS = 010: Prescale the internal clock by 8 */
TCCR0A = (0 << COM0A1) | (1 << COM0A0) | (1 << WGM01) | (0 << WGM00);
TCCR0B = (0 << WGM02) | (0 << CS02) | (1 << CS01) | (0 << CS00);
Ich denke, es ist diese Zeile, die die Quelle festlegen: 'TCCR0B | = (1 << CS02) | (1 << CS01) | (1 << CS00); '. Wenn alle drei gesetzt sind, bedeutet dies: ** Externe Taktquelle an T0-Pin. Uhr an steigender Flanke **. Wenn Sie keine externe Clock-Quelle auf ** T0 ** haben, stellen Sie einfach 'CS00' ein, um zum Beispiel die CPU-Frequenz als Quelle ohne Prescaler zu erhalten. –
Das funktioniert, habe ich jetzt am PB7 ausgegeben, aber die Frequenz ist jetzt zu hoch. Wenn ich SoundOutput (400) anrufe, kann ich eine O-Scope-Periode von 12.5us sehen, die für die Tonerzeugung zu hoch ist. –
Ja, weil die CPU-Frequenz des 2560 16 MHz beträgt. Die Dauer Ihres Tonsignals ist also: "t = (1/f_CPU) * uintTone/2". Soll der Parameter 'uintTone' die resultierende Frequenz sein? Ich werde es später veröffentlichen, da ich Zeit als Antwort habe. –