Merge git://git.kernel.org/pub/scm/linux/kernel/git/wim/linux-2.6-nvram
[linux-2.6] / drivers / isdn / mISDN / l1oip_codec.c
1 /*
2
3  * l1oip_codec.c  generic codec using lookup table
4  *  -> conversion from a-Law to u-Law
5  *  -> conversion from u-Law to a-Law
6  *  -> compression by reducing the number of sample resolution to 4
7  *
8  * NOTE: It is not compatible with any standard codec like ADPCM.
9  *
10  * Author       Andreas Eversberg (jolly@eversberg.eu)
11  *
12  * This program is free software; you can redistribute it and/or modify
13  * it under the terms of the GNU General Public License as published by
14  * the Free Software Foundation; either version 2, or (at your option)
15  * any later version.
16  *
17  * This program is distributed in the hope that it will be useful,
18  * but WITHOUT ANY WARRANTY; without even the implied warranty of
19  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20  * GNU General Public License for more details.
21  *
22  * You should have received a copy of the GNU General Public License
23  * along with this program; if not, write to the Free Software
24  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
25
26  */
27
28 /*
29
30 How the codec works:
31 --------------------
32
33 The volume is increased to increase the dynamic range of the audio signal.
34 Each sample is converted to a-LAW with only 16 steps of level resolution.
35 A pair of two samples are stored in one byte.
36
37 The first byte is stored in the upper bits, the second byte is stored in the
38 lower bits.
39
40 To speed up compression and decompression, two lookup tables are formed:
41
42 - 16 bits index for two samples (law encoded) with 8 bit compressed result.
43 - 8 bits index for one compressed data with 16 bits decompressed result.
44
45 NOTE: The bytes are handled as they are law-encoded.
46
47 */
48
49 #include <linux/vmalloc.h>
50 #include <linux/mISDNif.h>
51 #include "core.h"
52 #include "l1oip.h"
53
54 /* definitions of codec. don't use calculations, code may run slower. */
55
56 static u8 *table_com;
57 static u16 *table_dec;
58
59
60 /* alaw -> ulaw */
61 static u8 alaw_to_ulaw[256] =
62 {
63         0xab, 0x2b, 0xe3, 0x63, 0x8b, 0x0b, 0xc9, 0x49,
64         0xba, 0x3a, 0xf6, 0x76, 0x9b, 0x1b, 0xd7, 0x57,
65         0xa3, 0x23, 0xdd, 0x5d, 0x83, 0x03, 0xc1, 0x41,
66         0xb2, 0x32, 0xeb, 0x6b, 0x93, 0x13, 0xcf, 0x4f,
67         0xaf, 0x2f, 0xe7, 0x67, 0x8f, 0x0f, 0xcd, 0x4d,
68         0xbe, 0x3e, 0xfe, 0x7e, 0x9f, 0x1f, 0xdb, 0x5b,
69         0xa7, 0x27, 0xdf, 0x5f, 0x87, 0x07, 0xc5, 0x45,
70         0xb6, 0x36, 0xef, 0x6f, 0x97, 0x17, 0xd3, 0x53,
71         0xa9, 0x29, 0xe1, 0x61, 0x89, 0x09, 0xc7, 0x47,
72         0xb8, 0x38, 0xf2, 0x72, 0x99, 0x19, 0xd5, 0x55,
73         0xa1, 0x21, 0xdc, 0x5c, 0x81, 0x01, 0xbf, 0x3f,
74         0xb0, 0x30, 0xe9, 0x69, 0x91, 0x11, 0xce, 0x4e,
75         0xad, 0x2d, 0xe5, 0x65, 0x8d, 0x0d, 0xcb, 0x4b,
76         0xbc, 0x3c, 0xfa, 0x7a, 0x9d, 0x1d, 0xd9, 0x59,
77         0xa5, 0x25, 0xde, 0x5e, 0x85, 0x05, 0xc3, 0x43,
78         0xb4, 0x34, 0xed, 0x6d, 0x95, 0x15, 0xd1, 0x51,
79         0xac, 0x2c, 0xe4, 0x64, 0x8c, 0x0c, 0xca, 0x4a,
80         0xbb, 0x3b, 0xf8, 0x78, 0x9c, 0x1c, 0xd8, 0x58,
81         0xa4, 0x24, 0xde, 0x5e, 0x84, 0x04, 0xc2, 0x42,
82         0xb3, 0x33, 0xec, 0x6c, 0x94, 0x14, 0xd0, 0x50,
83         0xb0, 0x30, 0xe8, 0x68, 0x90, 0x10, 0xce, 0x4e,
84         0xbf, 0x3f, 0xfe, 0x7e, 0xa0, 0x20, 0xdc, 0x5c,
85         0xa8, 0x28, 0xe0, 0x60, 0x88, 0x08, 0xc6, 0x46,
86         0xb7, 0x37, 0xf0, 0x70, 0x98, 0x18, 0xd4, 0x54,
87         0xaa, 0x2a, 0xe2, 0x62, 0x8a, 0x0a, 0xc8, 0x48,
88         0xb9, 0x39, 0xf4, 0x74, 0x9a, 0x1a, 0xd6, 0x56,
89         0xa2, 0x22, 0xdd, 0x5d, 0x82, 0x02, 0xc0, 0x40,
90         0xb1, 0x31, 0xea, 0x6a, 0x92, 0x12, 0xcf, 0x4f,
91         0xae, 0x2e, 0xe6, 0x66, 0x8e, 0x0e, 0xcc, 0x4c,
92         0xbd, 0x3d, 0xfc, 0x7c, 0x9e, 0x1e, 0xda, 0x5a,
93         0xa6, 0x26, 0xdf, 0x5f, 0x86, 0x06, 0xc4, 0x44,
94         0xb5, 0x35, 0xee, 0x6e, 0x96, 0x16, 0xd2, 0x52
95 };
96
97 /* ulaw -> alaw */
98 static u8 ulaw_to_alaw[256] =
99 {
100         0xab, 0x55, 0xd5, 0x15, 0x95, 0x75, 0xf5, 0x35,
101         0xb5, 0x45, 0xc5, 0x05, 0x85, 0x65, 0xe5, 0x25,
102         0xa5, 0x5d, 0xdd, 0x1d, 0x9d, 0x7d, 0xfd, 0x3d,
103         0xbd, 0x4d, 0xcd, 0x0d, 0x8d, 0x6d, 0xed, 0x2d,
104         0xad, 0x51, 0xd1, 0x11, 0x91, 0x71, 0xf1, 0x31,
105         0xb1, 0x41, 0xc1, 0x01, 0x81, 0x61, 0xe1, 0x21,
106         0x59, 0xd9, 0x19, 0x99, 0x79, 0xf9, 0x39, 0xb9,
107         0x49, 0xc9, 0x09, 0x89, 0x69, 0xe9, 0x29, 0xa9,
108         0xd7, 0x17, 0x97, 0x77, 0xf7, 0x37, 0xb7, 0x47,
109         0xc7, 0x07, 0x87, 0x67, 0xe7, 0x27, 0xa7, 0xdf,
110         0x9f, 0x7f, 0xff, 0x3f, 0xbf, 0x4f, 0xcf, 0x0f,
111         0x8f, 0x6f, 0xef, 0x2f, 0x53, 0x13, 0x73, 0x33,
112         0xb3, 0x43, 0xc3, 0x03, 0x83, 0x63, 0xe3, 0x23,
113         0xa3, 0x5b, 0xdb, 0x1b, 0x9b, 0x7b, 0xfb, 0x3b,
114         0xbb, 0xbb, 0x4b, 0x4b, 0xcb, 0xcb, 0x0b, 0x0b,
115         0x8b, 0x8b, 0x6b, 0x6b, 0xeb, 0xeb, 0x2b, 0x2b,
116         0xab, 0x54, 0xd4, 0x14, 0x94, 0x74, 0xf4, 0x34,
117         0xb4, 0x44, 0xc4, 0x04, 0x84, 0x64, 0xe4, 0x24,
118         0xa4, 0x5c, 0xdc, 0x1c, 0x9c, 0x7c, 0xfc, 0x3c,
119         0xbc, 0x4c, 0xcc, 0x0c, 0x8c, 0x6c, 0xec, 0x2c,
120         0xac, 0x50, 0xd0, 0x10, 0x90, 0x70, 0xf0, 0x30,
121         0xb0, 0x40, 0xc0, 0x00, 0x80, 0x60, 0xe0, 0x20,
122         0x58, 0xd8, 0x18, 0x98, 0x78, 0xf8, 0x38, 0xb8,
123         0x48, 0xc8, 0x08, 0x88, 0x68, 0xe8, 0x28, 0xa8,
124         0xd6, 0x16, 0x96, 0x76, 0xf6, 0x36, 0xb6, 0x46,
125         0xc6, 0x06, 0x86, 0x66, 0xe6, 0x26, 0xa6, 0xde,
126         0x9e, 0x7e, 0xfe, 0x3e, 0xbe, 0x4e, 0xce, 0x0e,
127         0x8e, 0x6e, 0xee, 0x2e, 0x52, 0x12, 0x72, 0x32,
128         0xb2, 0x42, 0xc2, 0x02, 0x82, 0x62, 0xe2, 0x22,
129         0xa2, 0x5a, 0xda, 0x1a, 0x9a, 0x7a, 0xfa, 0x3a,
130         0xba, 0xba, 0x4a, 0x4a, 0xca, 0xca, 0x0a, 0x0a,
131         0x8a, 0x8a, 0x6a, 0x6a, 0xea, 0xea, 0x2a, 0x2a
132 };
133
134 /* alaw -> 4bit compression */
135 static u8 alaw_to_4bit[256] = {
136         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
137         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x00, 0x0b, 0x04,
138         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
139         0x0d, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
140         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
141         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x00, 0x0b, 0x04,
142         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
143         0x0d, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
144         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
145         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x00, 0x0b, 0x04,
146         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0d, 0x02,
147         0x0e, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
148         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
149         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x00, 0x0b, 0x04,
150         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
151         0x0d, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
152         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
153         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x00, 0x0b, 0x04,
154         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
155         0x0d, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
156         0x0e, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
157         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x01, 0x0a, 0x05,
158         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
159         0x0d, 0x02, 0x09, 0x07, 0x0f, 0x00, 0x0b, 0x04,
160         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
161         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x00, 0x0b, 0x04,
162         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
163         0x0d, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
164         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
165         0x0d, 0x02, 0x08, 0x07, 0x0f, 0x00, 0x0b, 0x04,
166         0x0e, 0x01, 0x0a, 0x05, 0x0f, 0x00, 0x0c, 0x03,
167         0x0d, 0x02, 0x09, 0x06, 0x0f, 0x00, 0x0b, 0x04,
168 };
169
170 /* 4bit -> alaw decompression */
171 static u8 _4bit_to_alaw[16] = {
172         0x5d, 0x51, 0xd9, 0xd7, 0x5f, 0x53, 0xa3, 0x4b,
173         0x2a, 0x3a, 0x22, 0x2e, 0x26, 0x56, 0x20, 0x2c,
174 };
175
176 /* ulaw -> 4bit compression */
177 static u8 ulaw_to_4bit[256] = {
178         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
179         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
180         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
181         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
182         0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
183         0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
184         0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
185         0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
186         0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03,
187         0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x04, 0x04,
188         0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
189         0x04, 0x04, 0x04, 0x04, 0x05, 0x05, 0x05, 0x05,
190         0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
191         0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06,
192         0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07,
193         0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x08,
194         0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f,
195         0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f,
196         0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f,
197         0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f,
198         0x0f, 0x0e, 0x0e, 0x0e, 0x0e, 0x0e, 0x0e, 0x0e,
199         0x0e, 0x0e, 0x0e, 0x0e, 0x0e, 0x0e, 0x0e, 0x0e,
200         0x0e, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d,
201         0x0d, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d,
202         0x0c, 0x0c, 0x0c, 0x0c, 0x0c, 0x0c, 0x0c, 0x0c,
203         0x0c, 0x0c, 0x0c, 0x0c, 0x0c, 0x0c, 0x0b, 0x0b,
204         0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b,
205         0x0b, 0x0b, 0x0b, 0x0b, 0x0a, 0x0a, 0x0a, 0x0a,
206         0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
207         0x09, 0x09, 0x09, 0x09, 0x09, 0x09, 0x09, 0x09,
208         0x09, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
209         0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
210 };
211
212 /* 4bit -> ulaw decompression */
213 static u8 _4bit_to_ulaw[16] = {
214         0x11, 0x21, 0x31, 0x40, 0x4e, 0x5c, 0x68, 0x71,
215         0xfe, 0xef, 0xe7, 0xdb, 0xcd, 0xbf, 0xaf, 0x9f,
216 };
217
218
219 /*
220  * Compresses data to the result buffer
221  * The result size must be at least half of the input buffer.
222  * The number of samples also must be even!
223  */
224 int
225 l1oip_law_to_4bit(u8 *data, int len, u8 *result, u32 *state)
226 {
227         int ii, i = 0, o = 0;
228
229         if (!len)
230                 return 0;
231
232         /* send saved byte and first input byte */
233         if (*state) {
234                 *result++ = table_com[(((*state)<<8)&0xff00) | (*data++)];
235                 len--;
236                 o++;
237         }
238
239         ii = len >> 1;
240
241         while (i < ii) {
242                 *result++ = table_com[(data[0]<<8) | (data[1])];
243                 data += 2;
244                 i++;
245                 o++;
246         }
247
248         /* if len has an odd number, we save byte for next call */
249         if (len & 1)
250                 *state = 0x100 + *data;
251         else
252                 *state = 0;
253
254         return o;
255 }
256
257 /* Decompress data to the result buffer
258  * The result size must be the number of sample in packet. (2 * input data)
259  * The number of samples in the result are even!
260  */
261 int
262 l1oip_4bit_to_law(u8 *data, int len, u8 *result)
263 {
264         int i = 0;
265         u16 r;
266
267         while (i < len) {
268                 r = table_dec[*data++];
269                 *result++ = r>>8;
270                 *result++ = r;
271                 i++;
272         }
273
274         return len << 1;
275 }
276
277
278 /*
279  * law conversion
280  */
281 int
282 l1oip_alaw_to_ulaw(u8 *data, int len, u8 *result)
283 {
284         int i = 0;
285
286         while (i < len) {
287                 *result++ = alaw_to_ulaw[*data++];
288                 i++;
289         }
290
291         return len;
292 }
293
294 int
295 l1oip_ulaw_to_alaw(u8 *data, int len, u8 *result)
296 {
297         int i = 0;
298
299         while (i < len) {
300                 *result++ = ulaw_to_alaw[*data++];
301                 i++;
302         }
303
304         return len;
305 }
306
307
308 /*
309  * generate/free compression and decompression table
310  */
311 void
312 l1oip_4bit_free(void)
313 {
314         if (table_dec)
315                 vfree(table_dec);
316         if (table_com)
317                 vfree(table_com);
318         table_com = NULL;
319         table_dec = NULL;
320 }
321
322 int
323 l1oip_4bit_alloc(int ulaw)
324 {
325         int i1, i2, c, sample;
326
327         /* in case, it is called again */
328         if (table_dec)
329                 return 0;
330
331         /* alloc conversion tables */
332         table_com = vmalloc(65536);
333         table_dec = vmalloc(512);
334         if (!table_com | !table_dec) {
335                 l1oip_4bit_free();
336                 return -ENOMEM;
337         }
338         memset(table_com, 0, 65536);
339         memset(table_dec, 0, 512);
340         /* generate compression table */
341         i1 = 0;
342         while (i1 < 256) {
343                 if (ulaw)
344                         c = ulaw_to_4bit[i1];
345                 else
346                         c = alaw_to_4bit[i1];
347                 i2 = 0;
348                 while (i2 < 256) {
349                         table_com[(i1<<8) | i2] |= (c<<4);
350                         table_com[(i2<<8) | i1] |= c;
351                         i2++;
352                 }
353                 i1++;
354         }
355
356         /* generate decompression table */
357         i1 = 0;
358         while (i1 < 16) {
359                 if (ulaw)
360                         sample = _4bit_to_ulaw[i1];
361                 else
362                         sample = _4bit_to_alaw[i1];
363                 i2 = 0;
364                 while (i2 < 16) {
365                         table_dec[(i1<<4) | i2] |= (sample<<8);
366                         table_dec[(i2<<4) | i1] |= sample;
367                         i2++;
368                 }
369                 i1++;
370         }
371
372         return 0;
373 }
374
375