voice.c 1.59 KB
Newer Older
Jacob Vosmaer's avatar
Jacob Vosmaer committed
1 2 3
#include "voice.h"
#include <avr/io.h>

4 5
// voicetab represents the physical hardware layout and parameters
struct {
Jacob Vosmaer's avatar
Jacob Vosmaer committed
6 7
	struct gate gate;
	struct dac dac;
8 9
} voicetab[] = {
    {.gate = {.port = &PORTC, .mask = _BV(0)},
Jacob Vosmaer's avatar
Jacob Vosmaer committed
10
     .dac = {.channel = 2, .offset = 57, .scale = 8381}},
11
    {.gate = {.port = &PORTC, .mask = _BV(1)},
Jacob Vosmaer's avatar
Jacob Vosmaer committed
12
     .dac = {.channel = 3, .offset = 48, .scale = 8381}},
13 14 15
    {.gate = {.port = &PORTC, .mask = _BV(2)},
     .dac = {.channel = 4, .offset = 50, .scale = 8383}},
    {.gate = {.port = &PORTC, .mask = _BV(3)},
Jacob Vosmaer's avatar
Jacob Vosmaer committed
16 17 18 19 20 21 22 23 24
     .dac = {.channel = 5, .offset = 55, .scale = 8382}},
    {.gate = {.port = &PORTD, .mask = _BV(3)},
     .dac = {.channel = 0, .offset = 50, .scale = 8382}},
    {.gate = {.port = &PORTD, .mask = _BV(4)},
     .dac = {.channel = 1, .offset = 57, .scale = 8380}},
    {.gate = {.port = &PORTD, .mask = _BV(5)},
     .dac = {.channel = 7, .offset = 40, .scale = 8382}},
    {.gate = {.port = &PORTD, .mask = _BV(6)},
     .dac = {.channel = 6, .offset = 52, .scale = 8382}},
Jacob Vosmaer's avatar
Jacob Vosmaer committed
25 26
};

Jacob Vosmaer's avatar
Jacob Vosmaer committed
27
uint8_t voice_map[NUM_VOICES] = {1, 2, 3, 4, 5, 6, 7};
Jacob Vosmaer's avatar
Jacob Vosmaer committed
28

Jacob Vosmaer's avatar
Jacob Vosmaer committed
29
struct gate *gate(uint8_t v) {
30 31 32
	if (v >= NUM_VOICES) {
		return 0;
	}
Jacob Vosmaer's avatar
Jacob Vosmaer committed
33

34 35
	return &voicetab[voice_map[v]].gate;
}
Jacob Vosmaer's avatar
Jacob Vosmaer committed
36

Jacob Vosmaer's avatar
Jacob Vosmaer committed
37
struct dac *dac(uint8_t v) {
38 39
	if (v >= NUM_VOICES) {
		return 0;
Jacob Vosmaer's avatar
Jacob Vosmaer committed
40 41
	}

42
	return &voicetab[voice_map[v]].dac;
Jacob Vosmaer's avatar
Jacob Vosmaer committed
43
}
44

45
// This tuning is chosen to be 'good enough' for the 8380-8382 scale range above
46
const int16_t dac_semitones[NUM_SEMITONES] = {
47
    0, 698, 1397, 2095, 2794, 3492, 4191, 4889, 5587, 6286, 6984, 7683};
48

Jacob Vosmaer's avatar
Jacob Vosmaer committed
49
int16_t dac_semitone_offset(uint8_t semitone) {
50 51 52 53 54 55
	if (semitone >= NUM_SEMITONES) {
		return 0;
	}

	return dac_semitones[semitone];
}