diff options
author | Nao Pross <naopross@thearcway.org> | 2018-02-27 10:37:33 +0100 |
---|---|---|
committer | Nao Pross <naopross@thearcway.org> | 2018-02-27 10:37:33 +0100 |
commit | ad0f6d4291e8ca7fc60b07403a97b8661dffef72 (patch) | |
tree | 302da8c6651452b148360d009879aa3780e7fd64 | |
parent | Add LaTeX PDF output to git (diff) | |
download | Xilofono-ad0f6d4291e8ca7fc60b07403a97b8661dffef72.tar.gz Xilofono-ad0f6d4291e8ca7fc60b07403a97b8661dffef72.zip |
Finalize measurement code and implement midi output
-rw-r--r-- | src/main.c | 108 | ||||
-rw-r--r-- | src/midi.c | 8 | ||||
-rw-r--r-- | src/midi.h | 1 | ||||
-rw-r--r-- | src/rs232.c | 39 | ||||
-rw-r--r-- | src/rs232.h | 10 |
5 files changed, 116 insertions, 50 deletions
@@ -87,12 +87,25 @@ #include <stdint.h> #include <string.h> -#define NOTES 15 -#define NOTE_MASK 0xFF00 + +#define NOTE_MIN_LENGTH_MS 10 +#define NOTE_MASK 0xFFFFFF00 + +#define NOTES 16 + +#define MIDI_CHANNEL 0x0 +#define MIDI_SCALE_START 0x34 // note C3, C4 is 0x3C +#define MIDI_NOTE_SPEED 0x0F // max is 0x7F + + +#define DEBUG + /* global variables */ -volatile uint16_t keypresses[NOTES]; +volatile uint32_t keys_data[NOTES]; +// flags to notify the main program +volatile uint16_t keypresses = 0; /* function prototypes */ int eusart_write_midi(const midi_message_t *pkt); @@ -100,35 +113,33 @@ int eusart_write_midi(const midi_message_t *pkt); /* interrupt service routine */ interrupt void isr(void) { - unsigned char i, data; + unsigned char i, data_a, data_b; PORTDbits.RD3 = 0; if (PIR1bits.TMR2IF) { - // PORTA - data = PORTA; + data_a = PORTA; + data_b = PORTB; i = 7; do { - keypresses[i] = (keypresses[i] << 1) | ((data >> i) & 0x01); + // read the data and append it at the end of keys_data[i] + keys_data[i] = (keys_data[i] << 1) | ((data_a >> i) & 0x01); + keys_data[i + 8] = (keys_data[i + 8] << 1) | ((data_b >> i) & 0x01); + + // TODO same for PORTD when the steps board is printed + + // set flags + keypresses |= (keys_data[i] && !(keys_data[i] & NOTE_MASK))<<i; + keypresses |= (keys_data[i + 8] && !(keys_data[i + 8] & NOTE_MASK))<<(i + 8); + } while (i--); - data = PORTB; - i = 7; - do { - keypresses[i] = (keypresses[i] << 1) | ((data >> i) & 0x01); - } while (i-- - 8); - - // PORTB - // for (i = 8; i < NOTES; i++) { - // keypresses[i] = (keypresses[i] << 1) | ((PORTB & (1 << i)) >> i); - // } - - // TODO same for PORTD when the steps board is printed - +#ifdef DEBUG // debug stuff PORTDbits.RD4 = PORTAbits.RA0; - PORTDbits.RD2 = (keypresses[0] && !(keypresses[0] & NOTE_MASK)); - + PORTDbits.RD2 = (keys_data[0] && !(keys_data[0] & NOTE_MASK)); +#endif + // reset interrupt flag PIR1bits.TMR2IF = 0; } @@ -158,10 +169,11 @@ inline void init_hw(void) ANSELC = 0x00; ANSELD = 0x00; - // TODO: remove demo + // set ports as input TRISA = 0xFF; TRISB = 0xFF; +#ifdef DEBUG TRISDbits.TRISD1 = 0; TRISDbits.TRISD2 = 0; TRISDbits.TRISD3 = 0; @@ -175,12 +187,13 @@ inline void init_hw(void) PORTDbits.RD3 = 1; // TEST OUTPUT 3 PORTDbits.RD4 = 0; - +#endif + /* timer configuration */ // timer 2 comp value PR2 = 128; - // postscaler 1:4 - T2CONbits.T2OUTPS = 0b0011; + // postscaler 1:2 + T2CONbits.T2OUTPS = 0b0001; // prescaler 1:16 T2CONbits.T2CKPS = 0b11; // start timer @@ -195,30 +208,53 @@ inline void init_hw(void) /* serial configuration */ eusart1_init(); - - ei(); + eusart2_init(); } /* main program */ void main(void) { - unsigned char i, data; - midi_message_t sample_message; + unsigned i; + midi_message_t message; /* setup hardware */ init_hw(); /* setup software */ - memset(keypresses, 0, sizeof(keypresses)); + memset(keys_data, 0, sizeof(keys_data)); - /* TODO remove demo code */ - midi_note_on(&sample_message, 0x0, 0x3C, 0x7F); + ei(); + +#ifdef DEBUG PORTDbits.RD1 = 0; +#endif + + midi_note_on(&message, MIDI_CHANNEL, MIDI_SCALE_START, MIDI_NOTE_SPEED); /* main loop */ while (1) { - eusart_write_midi(&sample_message); + // check flags + for (i = 0; i < NOTES; i++) { + if (keypresses & (1<<i)) { + + // dirty hack to avoid the slow call stack, correct version commented below + message.data[0] = MIDI_SCALE_START + i; + // midi_note_on(&message, MIDI_CHANNEL, MIDI_SCALE_START + i, 0x7F); + + eusart_write_midi(&message); + + // wait for the minimum note length + + // TODO improve; + // with this system packets will be delayed by + // NOTE_MIN_LENGTH_MS * NOTES milliseconds relative to the actual measurement + __delay_ms(NOTE_MIN_LENGTH_MS); + + // unset flag + keypresses &= ~(1<<i); + } + } } } @@ -235,10 +271,10 @@ int eusart_write_midi(const midi_message_t *pkt) length = pkt->data_size; data = (uint8_t *) pkt->data; - putch((char)((pkt->status << 4) | pkt->channel)); + eusart2_putch((char)((pkt->status << 4) | pkt->channel)); while (length--) { - putch((char) *(data++)); + eusart2_putch((char) *(data++)); } return 0; @@ -64,10 +64,12 @@ int midi_note_on(midi_message_t *pkt, unsigned channel, midi_note_t note, uint8_ if (pkt == NULL) { return -1; } - + +#ifdef MIDI_DYNAMIC_MEMORY_ALLOC if (pkt->data == NULL) { return -2; } +#endif midi_set_status(pkt, NOTE_ON); midi_set_channel(pkt, channel); @@ -87,10 +89,12 @@ int midi_note_off(midi_message_t *pkt, unsigned channel, midi_note_t note, uint8 if (pkt == NULL) { return -1; } - + +#ifdef MIDI_DYNAMIC_MEMORY_ALLOC if (pkt->data == NULL) { return -2; } +#endif midi_set_status(pkt, NOTE_OFF); midi_set_channel(pkt, channel); @@ -53,7 +53,6 @@ typedef struct { #endif } midi_message_t; -extern unsigned midi_base_scale = 0x3C; /* MIDI API */ #ifdef MIDI_DYNAMIC_MEMORY_ALLOC diff --git a/src/rs232.c b/src/rs232.c index e060759..3fba3b4 100644 --- a/src/rs232.c +++ b/src/rs232.c @@ -17,31 +17,54 @@ void eusart1_init(void) // set up TX / RX pins TRISCbits.TRISC7 = 1; TRISCbits.TRISC6 = 1; - RCSTA1bits.CREN = 1; // enable continuous reception + // enable continuous reception + RCSTA1bits.CREN = 1; TXSTA1bits.TXEN = 1; } void eusart2_init(void) { - // TODO + // set Async and 8 bits frame + TXSTA2bits.SYNC = 0; + TXSTA2bits.TX9 = 0; + + // baud prescaler + RCSTA2bits.SPEN = 1; + SPBRG2 = 31; + SPBRGH2 = 0; + TXSTA2bits.BRGH = 0; + BAUDCON2bits.BRG16 = 0; + + // set up TX / RX pins + TRISDbits.TRISD7 = 1; + TRISDbits.TRISD6 = 1; + // enable continuous reception + RCSTA2bits.CREN = 1; + TXSTA2bits.TXEN = 1; } -void putch(char c) +void eusart1_putch(char c) { while (!TX1IF); TX1REG = c; } -char getch(void) +void eusart2_putch(char c) +{ + while (!TX2IF); + TX2REG = c; +} + +char eusart1_getch(void) { while (!RC1IF); return RC1REG; } -char getche(void) +char eusart1_getche(void) { - char c = getch(); - putch(c); // echo + char c = eusart1_getch(); + eusart1_putch(c); // echo return c; -} +}
\ No newline at end of file diff --git a/src/rs232.h b/src/rs232.h index cb59df0..4a9f42a 100644 --- a/src/rs232.h +++ b/src/rs232.h @@ -12,9 +12,13 @@ extern void eusart1_init(void); extern void eusart2_init(void); -extern void putch(char c); -extern char getch(void); -extern char getche(void); +extern void eusart1_putch(char c); +extern void eusart2_putch(char c); + +extern char eusart1_getch(void); + +extern char eusart1_getche(void); + #endif /* RS232_H */ |