4 * Copyright by Andreas Eversberg (jolly@eversberg.eu)
6 * This software may be used and distributed according to the terms
7 * of the GNU General Public License, incorporated herein by reference.
12 #include "ss5_encode.h"
15 static double ss5_freq[9][2] = {
17 {700, 0.19952623}, /* 1: 700, -7db */
18 {900, 0.19952623}, /* 2: 900, -7db */
19 {1100, 0.19952623}, /* 3: 1100, -7db */
20 {1300, 0.19952623}, /* 4: 1300, -7db */
21 {1500, 0.19952623}, /* 5: 1500, -7db */
22 {1700, 0.19952623}, /* 6: 1700, -7db */
23 {2400, 0.12589254}, /* 7: 2400, -9db */
24 {2600, 0.12589254}, /* 8: 2600, -9db */
27 static char ss5_digits[][3] = {
38 {'*', 1, 6}, /* code 11 */
39 {'#', 2, 6}, /* code 12 */
40 {'a', 3, 6}, /* KP1 */
41 {'b', 4, 6}, /* KP2 */
43 {'A', 7, 0}, /* 2400 answer, acknowledge */
44 {'B', 8, 0}, /* 2600 busy */
45 {'C', 7, 8}, /* 2600+2400 clear forward */
49 static unsigned char sintab[15+3][8192]; /* sine tables of about one second sound (error <1Hz) */
51 /* generate sine tables */
52 void ss5_sine_generate(void)
56 double vol1, vol2, phase1, phase2;
59 for (i = 0; i < 15+3; i++) {
60 /* how many cycles are within 8192 samples (rounded!) */
61 cycles1 = (int)(ss5_freq[(int)ss5_digits[i][1]][0] / 8000.0 * 8192.0 + 0.5);
62 cycles2 = (int)(ss5_freq[(int)ss5_digits[i][2]][0] / 8000.0 * 8192.0 + 0.5);
63 /* how much phase shift within one cycle */
64 phase1 = 2.0 * 3.14159265 * cycles1 / 8192.0;
65 phase2 = 2.0 * 3.14159265 * cycles2 / 8192.0;
67 vol1 = ss5_freq[(int)ss5_digits[i][1]][1] * 32768.0;
68 vol2 = ss5_freq[(int)ss5_digits[i][2]][1] * 32768.0;
69 for (j = 0; j < 8192; j++) {
70 sample = (int)(sin(phase1 * j) * vol1);
71 sample += (int)(sin(phase2 * j) * vol2);
72 sintab[i][j] = audio_s16_to_law[sample & 0xffff];
77 /* encode digit at given sample_nr with given lengt and return law-encoded audio */
78 unsigned char *ss5_encode(unsigned char *buffer, int len, char digit, int sample_nr)
82 /* get frequency from digit */
84 while(ss5_digits[i][0]) {
85 if (digit == ss5_digits[i][0])
89 if (!ss5_digits[i][0]) {
90 PERROR("Digit '%c' does not exist.\n", digit);
91 memset(buffer, audio_s16_to_law[0], sizeof(buffer));
96 for (j = 0; j < len; j++)
97 *buffer++ = sintab[i][sample_nr++ & 8191];