Added code

This commit is contained in:
David Lenfesty 2019-10-19 22:15:38 -06:00
parent 80d55f25b0
commit 2d4a3fba3e
4 changed files with 392 additions and 0 deletions

151
lab_2/main.c Normal file
View File

@ -0,0 +1,151 @@
/*
* GccApplication1.c
*
* Created: 10/8/2019 2:07:13 PM
* Author : lenfesty
*/
#include "main.h"
uint8_t play_flag = 0;
uint8_t button_flag = 0;
ISR(INT0_vect) {
// Disable interrupts
cli();
// Notify of button press
button_flag = 1;
}
/*
* Pin Definitions:
* PB2 -> OC0A output
* PB3 -> OC1A output
* PB0 -> Switch Input
*/
void gpio_init() {
// Piezo Out
DDRB |= (1 << DDB2) | (1 << DDB3);
// Switch Input Setup
DDRD &= ~(1 << DDD2);
PORTD |= (1 << PORTD2);
// Configure Interrupt Stuff
// Set falling edge for INT0
MCUCR |= (1 << ISC01) | (0 << ISC00);
// Enable INT0
GIMSK |= (1 << INT0);
}
void timer_init( ) {
/* --- Timer 0 (8 bit) --- */
// Set Compare mode A to toggle, and waveform generation mode to CTC
TCCR0A = (0 << COM0A1) | (1 << COM0A0) | (1 << WGM01) | (0 << WGM00);
// Nothing else relevant here, without setting notes
/* --- Timer 1 (16 bit) --- */
// Set compare mode A to toggle
TCCR1A = (0 << COM1A1) | (1 << COM1A0);
// Set waveform gen mode to CTC
TCCR1B = (1 << WGM12);
}
void play_beat() {
static uint8_t duration_left[2] = {0};
static uint16_t song_location[2] = {0};
// If at end of song, restart
if (song_location[0] == SPEAKER0_LEN) {
song_location[0] = 0;
song_location[1] = 0;
}
// Set note
for (uint8_t speaker = 0; speaker < 2; speaker++) {
if (duration_left[speaker] == 0) {
// Move to next note
// Read in next note from program memory
uint16_t beat;
beat_t* p_beat;
// Select from correct song
if (speaker == 0) {
beat = pgm_read_word((PGM_P*) &song_speaker0[song_location[speaker]]);
} else {
beat = pgm_read_word((PGM_P*) &song_speaker1[song_location[speaker]]);
}
p_beat = (beat_t*) &beat;
// Set duration left after this beat
duration_left[speaker] = p_beat->duration - 1;
// Increment song location for next note
song_location[speaker]++;
// actually set note
play_note(*p_beat, speaker);
} else {
// Keep handling current note
// do nothing, it is set correctly
duration_left[speaker]--;
}
}
_delay_ms(BEAT_LENGTH * (1 - REST_FRACTION)); // Play note
// Rest note if at the end of the interval
for (uint8_t speaker = 0; speaker < 2; speaker++) {
if (duration_left[speaker] == 0) {
// End of note, pause here
beat_t beat = {
.note = rest,
.duration = 0,
.octave = 0, // octave doesn't matter, its a rest
};
play_note(beat, speaker);
} else {
// Note does not end, change nothing
}
}
_delay_ms(BEAT_LENGTH * REST_FRACTION);
}
int main(void)
{
gpio_init();
timer_init();
sei();
/* Replace with your application code */
while (1)
{
if (play_flag) {
play_beat();
}
if (button_flag) {
button_flag = 0;
beat_t beat = {
.note = rest,
};
play_note(beat, 0);
play_note(beat, 1);
_delay_ms(100);
sei();
}
if ( bit_is_clear(PIND, PIND2) && (play_flag == 0)) {
cli();
play_flag = 1;
_delay_ms(100);
sei();
}
}
}

42
lab_2/main.h Normal file
View File

@ -0,0 +1,42 @@
#ifndef MAIN_H_
#define MAIN_H_
#define F_CPU 8000000UL
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>
#include <util/delay.h>
#include "notes.h"
#define TEMPO (120 * 4) // Tempo of song (bpm)
#define REST_FRACTION 0.3 // Fraction of the beat to stay silent between notes
#define BEAT_LENGTH 60000 / TEMPO // Length of each note (ms)
#define OCTAVES 2
#define NOTES_PER_OCTAVE 12
#define SPEAKER0_LEN 38
#define SPEAKER1_LEN 96
typedef enum {
a = 0, b, c, d, e, f, g,
A, C, D, F, G,
rest
} note_t;
typedef struct {
note_t note;
uint8_t duration:7;
uint8_t octave:1;
} beat_t;
extern const uint8_t PROGMEM notes[OCTAVES][NOTES_PER_OCTAVE];
extern const beat_t PROGMEM song_speaker0[SPEAKER0_LEN];
extern const beat_t PROGMEM song_speaker1[SPEAKER1_LEN];
void play_note(beat_t note, uint8_t speaker);
#endif

58
lab_2/notes.c Normal file
View File

@ -0,0 +1,58 @@
#include "main.h"
/*
const uint8_t PROGMEM notes[OCTAVES][NOTES_PER_OCTAVE] = {
{ 140, 62, 118, 106, 94, 88, 79, 64, 112, 98, , 37 }, // 1024 prescaler octave 2
{ 141, 126, 238, 212, 188, 178, 158, 133, 225, 200, 168, 150 } // 64 prescaler octave 4
};
*/
const uint8_t PROGMEM notes[OCTAVES][NOTES_PER_OCTAVE] = {
{ 35, 31, 59, 53, 47, 44, 39, 32, 56, 49, 41, 37 }, // 1024 prescaler octave 2
{ 141, 126, 238, 212, 188, 178, 158, 133, 225, 200, 168, 150 } // 64 prescaler octave 4
};
void play_note(beat_t note, uint8_t speaker) {
if (note.note == rest) { // Handle special rest case
if (speaker == 0) {
// Turn off timer clock source, disabling
TCCR0B &= ~( (1 << CS02) | (1 << CS01) | (1 << CS00));
// Turn off output pin
PORTB &= ~(1 << PORTB2);
} else {
// turn off timer clock source, disabling
TCCR1B &= ~( (1 << CS12) | (1 << CS11) | (1 << CS10));
// turn off output pin
PORTB &= ~(1 << PORTB3);
}
} else {
// Set up so note changes always happen after rests,
// so we know CS[2:0] = 0
// See pages 86 and 114
uint8_t prescale = 0;
if (note.octave == 0) {
// set prescaler to 1024
prescale = 4;
} else {
// set prescaler to 64
prescale = 3;
}
// Get value to write to output compare
uint8_t period = pgm_read_byte((PGM_P*) &notes[note.octave][note.note]);
// Actually set clock source
if (speaker == 0) {
TCNT0 = 0; // reset counter
OCR0A = period; // set note period
TCCR0B |= prescale;
} else {
TCNT1H = 0; // reset counter
TCNT1L = 0;
OCR1AL = period; // set note period
OCR1AH = period >> 8;
TCCR1B |= prescale;
}
}
}

141
lab_2/song.c Normal file
View File

@ -0,0 +1,141 @@
#include "main.h"
const beat_t PROGMEM song_speaker0[SPEAKER0_LEN] = {
{.note = g, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = d, .duration = 6, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = g, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = f, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = d, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
{.note = c, .duration = 4, .octave = 0 },
};
const beat_t PROGMEM song_speaker1[SPEAKER1_LEN] = {
{.note = d, .duration = 2, .octave = 1 },
{.note = A, .duration = 2, .octave = 1 },
{.note = g, .duration = 2, .octave = 1 },
{.note = g, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = e, .duration = 2, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = A, .duration = 2, .octave = 1 },
{.note = g, .duration = 2, .octave = 1 },
{.note = g, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 3, .octave = 1 },
{.note = e, .duration = 2, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = A, .duration = 2, .octave = 1 },
{.note = g, .duration = 2, .octave = 1 },
{.note = g, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = e, .duration = 2, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = A, .duration = 2, .octave = 1 },
{.note = g, .duration = 2, .octave = 1 },
{.note = g, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = e, .duration = 2, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = A, .duration = 2, .octave = 1 },
{.note = g, .duration = 2, .octave = 1 },
{.note = g, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = d, .duration = 2, .octave = 1 },
{.note = d, .duration = 1, .octave = 1 },
{.note = a, .duration = 2, .octave = 1 },
{.note = f, .duration = 2, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = c, .duration = 2, .octave = 1 },
{.note = e, .duration = 2, .octave = 1 },
{.note = e, .duration = 1, .octave = 1 },
{.note = f, .duration = 1, .octave = 1 },
{.note = e, .duration = 1, .octave = 1},
};