alaw.c revision 1.4 1 1.4 skrll /* $NetBSD: alaw.c,v 1.4 2021/07/21 06:35:44 skrll Exp $ */
2 1.2 isaki
3 1.2 isaki /*
4 1.2 isaki * Copyright (C) 2018 Tetsuya Isaki. All rights reserved.
5 1.2 isaki *
6 1.2 isaki * Redistribution and use in source and binary forms, with or without
7 1.2 isaki * modification, are permitted provided that the following conditions
8 1.2 isaki * are met:
9 1.2 isaki * 1. Redistributions of source code must retain the above copyright
10 1.2 isaki * notice, this list of conditions and the following disclaimer.
11 1.2 isaki * 2. Redistributions in binary form must reproduce the above copyright
12 1.2 isaki * notice, this list of conditions and the following disclaimer in the
13 1.2 isaki * documentation and/or other materials provided with the distribution.
14 1.2 isaki *
15 1.2 isaki * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
16 1.2 isaki * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
17 1.2 isaki * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
18 1.2 isaki * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
19 1.2 isaki * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
20 1.2 isaki * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
21 1.2 isaki * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
22 1.2 isaki * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
23 1.2 isaki * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24 1.2 isaki * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25 1.2 isaki * SUCH DAMAGE.
26 1.2 isaki */
27 1.2 isaki
28 1.2 isaki #include <sys/cdefs.h>
29 1.4 skrll __KERNEL_RCSID(0, "$NetBSD: alaw.c,v 1.4 2021/07/21 06:35:44 skrll Exp $");
30 1.2 isaki
31 1.4 skrll #include <sys/param.h>
32 1.2 isaki #include <sys/types.h>
33 1.2 isaki #include <sys/systm.h>
34 1.2 isaki #include <sys/device.h>
35 1.2 isaki #include <dev/audio/audiovar.h>
36 1.2 isaki #include <dev/audio/mulaw.h>
37 1.2 isaki
38 1.2 isaki static const uint16_t alaw_to_slinear16[256] = {
39 1.2 isaki 0xea80, 0xeb80, 0xe880, 0xe980, 0xee80, 0xef80, 0xec80, 0xed80,
40 1.2 isaki 0xe280, 0xe380, 0xe080, 0xe180, 0xe680, 0xe780, 0xe480, 0xe580,
41 1.2 isaki 0xf540, 0xf5c0, 0xf440, 0xf4c0, 0xf740, 0xf7c0, 0xf640, 0xf6c0,
42 1.2 isaki 0xf140, 0xf1c0, 0xf040, 0xf0c0, 0xf340, 0xf3c0, 0xf240, 0xf2c0,
43 1.2 isaki 0xaa00, 0xae00, 0xa200, 0xa600, 0xba00, 0xbe00, 0xb200, 0xb600,
44 1.2 isaki 0x8a00, 0x8e00, 0x8200, 0x8600, 0x9a00, 0x9e00, 0x9200, 0x9600,
45 1.2 isaki 0xd500, 0xd700, 0xd100, 0xd300, 0xdd00, 0xdf00, 0xd900, 0xdb00,
46 1.2 isaki 0xc500, 0xc700, 0xc100, 0xc300, 0xcd00, 0xcf00, 0xc900, 0xcb00,
47 1.2 isaki 0xfea8, 0xfeb8, 0xfe88, 0xfe98, 0xfee8, 0xfef8, 0xfec8, 0xfed8,
48 1.2 isaki 0xfe28, 0xfe38, 0xfe08, 0xfe18, 0xfe68, 0xfe78, 0xfe48, 0xfe58,
49 1.2 isaki 0xffa8, 0xffb8, 0xff88, 0xff98, 0xffe8, 0xfff8, 0xffc8, 0xffd8,
50 1.2 isaki 0xff28, 0xff38, 0xff08, 0xff18, 0xff68, 0xff78, 0xff48, 0xff58,
51 1.2 isaki 0xfaa0, 0xfae0, 0xfa20, 0xfa60, 0xfba0, 0xfbe0, 0xfb20, 0xfb60,
52 1.2 isaki 0xf8a0, 0xf8e0, 0xf820, 0xf860, 0xf9a0, 0xf9e0, 0xf920, 0xf960,
53 1.2 isaki 0xfd50, 0xfd70, 0xfd10, 0xfd30, 0xfdd0, 0xfdf0, 0xfd90, 0xfdb0,
54 1.2 isaki 0xfc50, 0xfc70, 0xfc10, 0xfc30, 0xfcd0, 0xfcf0, 0xfc90, 0xfcb0,
55 1.2 isaki 0x1580, 0x1480, 0x1780, 0x1680, 0x1180, 0x1080, 0x1380, 0x1280,
56 1.2 isaki 0x1d80, 0x1c80, 0x1f80, 0x1e80, 0x1980, 0x1880, 0x1b80, 0x1a80,
57 1.2 isaki 0x0ac0, 0x0a40, 0x0bc0, 0x0b40, 0x08c0, 0x0840, 0x09c0, 0x0940,
58 1.2 isaki 0x0ec0, 0x0e40, 0x0fc0, 0x0f40, 0x0cc0, 0x0c40, 0x0dc0, 0x0d40,
59 1.2 isaki 0x5600, 0x5200, 0x5e00, 0x5a00, 0x4600, 0x4200, 0x4e00, 0x4a00,
60 1.2 isaki 0x7600, 0x7200, 0x7e00, 0x7a00, 0x6600, 0x6200, 0x6e00, 0x6a00,
61 1.2 isaki 0x2b00, 0x2900, 0x2f00, 0x2d00, 0x2300, 0x2100, 0x2700, 0x2500,
62 1.2 isaki 0x3b00, 0x3900, 0x3f00, 0x3d00, 0x3300, 0x3100, 0x3700, 0x3500,
63 1.2 isaki 0x0158, 0x0148, 0x0178, 0x0168, 0x0118, 0x0108, 0x0138, 0x0128,
64 1.2 isaki 0x01d8, 0x01c8, 0x01f8, 0x01e8, 0x0198, 0x0188, 0x01b8, 0x01a8,
65 1.2 isaki 0x0058, 0x0048, 0x0078, 0x0068, 0x0018, 0x0008, 0x0038, 0x0028,
66 1.2 isaki 0x00d8, 0x00c8, 0x00f8, 0x00e8, 0x0098, 0x0088, 0x00b8, 0x00a8,
67 1.2 isaki 0x0560, 0x0520, 0x05e0, 0x05a0, 0x0460, 0x0420, 0x04e0, 0x04a0,
68 1.2 isaki 0x0760, 0x0720, 0x07e0, 0x07a0, 0x0660, 0x0620, 0x06e0, 0x06a0,
69 1.2 isaki 0x02b0, 0x0290, 0x02f0, 0x02d0, 0x0230, 0x0210, 0x0270, 0x0250,
70 1.2 isaki 0x03b0, 0x0390, 0x03f0, 0x03d0, 0x0330, 0x0310, 0x0370, 0x0350,
71 1.2 isaki };
72 1.2 isaki
73 1.2 isaki static const uint8_t slinear8_to_alaw[256] = {
74 1.2 isaki 0xd5, 0xc5, 0xf5, 0xfd, 0xe5, 0xe1, 0xed, 0xe9,
75 1.2 isaki 0x95, 0x97, 0x91, 0x93, 0x9d, 0x9f, 0x99, 0x9b,
76 1.2 isaki 0x85, 0x84, 0x87, 0x86, 0x81, 0x80, 0x83, 0x82,
77 1.2 isaki 0x8d, 0x8c, 0x8f, 0x8e, 0x89, 0x88, 0x8b, 0x8a,
78 1.2 isaki 0xb5, 0xb5, 0xb4, 0xb4, 0xb7, 0xb7, 0xb6, 0xb6,
79 1.2 isaki 0xb1, 0xb1, 0xb0, 0xb0, 0xb3, 0xb3, 0xb2, 0xb2,
80 1.2 isaki 0xbd, 0xbd, 0xbc, 0xbc, 0xbf, 0xbf, 0xbe, 0xbe,
81 1.2 isaki 0xb9, 0xb9, 0xb8, 0xb8, 0xbb, 0xbb, 0xba, 0xba,
82 1.2 isaki 0xa5, 0xa5, 0xa5, 0xa5, 0xa4, 0xa4, 0xa4, 0xa4,
83 1.2 isaki 0xa7, 0xa7, 0xa7, 0xa7, 0xa6, 0xa6, 0xa6, 0xa6,
84 1.2 isaki 0xa1, 0xa1, 0xa1, 0xa1, 0xa0, 0xa0, 0xa0, 0xa0,
85 1.2 isaki 0xa3, 0xa3, 0xa3, 0xa3, 0xa2, 0xa2, 0xa2, 0xa2,
86 1.2 isaki 0xad, 0xad, 0xad, 0xad, 0xac, 0xac, 0xac, 0xac,
87 1.2 isaki 0xaf, 0xaf, 0xaf, 0xaf, 0xae, 0xae, 0xae, 0xae,
88 1.2 isaki 0xa9, 0xa9, 0xa9, 0xa9, 0xa8, 0xa8, 0xa8, 0xa8,
89 1.2 isaki 0xab, 0xab, 0xab, 0xab, 0xaa, 0xaa, 0xaa, 0xaa,
90 1.2 isaki 0x2a, 0x2a, 0x2a, 0x2a, 0x2b, 0x2b, 0x2b, 0x2b,
91 1.2 isaki 0x28, 0x28, 0x28, 0x28, 0x29, 0x29, 0x29, 0x29,
92 1.2 isaki 0x2e, 0x2e, 0x2e, 0x2e, 0x2f, 0x2f, 0x2f, 0x2f,
93 1.2 isaki 0x2c, 0x2c, 0x2c, 0x2c, 0x2d, 0x2d, 0x2d, 0x2d,
94 1.2 isaki 0x22, 0x22, 0x22, 0x22, 0x23, 0x23, 0x23, 0x23,
95 1.2 isaki 0x20, 0x20, 0x20, 0x20, 0x21, 0x21, 0x21, 0x21,
96 1.2 isaki 0x26, 0x26, 0x26, 0x26, 0x27, 0x27, 0x27, 0x27,
97 1.2 isaki 0x24, 0x24, 0x24, 0x24, 0x25, 0x25, 0x25, 0x25,
98 1.2 isaki 0x3a, 0x3a, 0x3b, 0x3b, 0x38, 0x38, 0x39, 0x39,
99 1.2 isaki 0x3e, 0x3e, 0x3f, 0x3f, 0x3c, 0x3c, 0x3d, 0x3d,
100 1.2 isaki 0x32, 0x32, 0x33, 0x33, 0x30, 0x30, 0x31, 0x31,
101 1.2 isaki 0x36, 0x36, 0x37, 0x37, 0x34, 0x34, 0x35, 0x35,
102 1.2 isaki 0x0a, 0x0b, 0x08, 0x09, 0x0e, 0x0f, 0x0c, 0x0d,
103 1.2 isaki 0x02, 0x03, 0x00, 0x01, 0x06, 0x07, 0x04, 0x05,
104 1.2 isaki 0x1a, 0x18, 0x1e, 0x1c, 0x12, 0x10, 0x16, 0x14,
105 1.2 isaki 0x6a, 0x6e, 0x62, 0x66, 0x7a, 0x72, 0x4a, 0x5a,
106 1.2 isaki };
107 1.2 isaki
108 1.2 isaki /*
109 1.2 isaki * audio_alaw_to_internal:
110 1.2 isaki * This filter performs conversion from A-law to internal format.
111 1.2 isaki */
112 1.2 isaki void
113 1.2 isaki audio_alaw_to_internal(audio_filter_arg_t *arg)
114 1.2 isaki {
115 1.2 isaki const uint8_t *s;
116 1.2 isaki aint_t *d;
117 1.2 isaki u_int sample_count;
118 1.2 isaki u_int i;
119 1.2 isaki
120 1.2 isaki DIAGNOSTIC_filter_arg(arg);
121 1.2 isaki KASSERT(arg->srcfmt->encoding == AUDIO_ENCODING_ALAW);
122 1.2 isaki KASSERT(arg->srcfmt->stride == 8);
123 1.2 isaki KASSERT(arg->srcfmt->precision == 8);
124 1.2 isaki KASSERT(audio_format2_is_internal(arg->dstfmt));
125 1.2 isaki KASSERT(arg->srcfmt->channels == arg->dstfmt->channels);
126 1.2 isaki
127 1.2 isaki s = arg->src;
128 1.2 isaki d = arg->dst;
129 1.2 isaki sample_count = arg->count * arg->srcfmt->channels;
130 1.2 isaki
131 1.2 isaki for (i = 0; i < sample_count; i++) {
132 1.2 isaki aint_t val;
133 1.2 isaki val = alaw_to_slinear16[*s++];
134 1.2 isaki val <<= AUDIO_INTERNAL_BITS - 16;
135 1.2 isaki *d++ = val;
136 1.2 isaki }
137 1.2 isaki }
138 1.2 isaki
139 1.2 isaki /*
140 1.2 isaki * audio_internal_to_alaw:
141 1.2 isaki * This filter performs conversion from internal format to A-law.
142 1.2 isaki */
143 1.2 isaki void
144 1.2 isaki audio_internal_to_alaw(audio_filter_arg_t *arg)
145 1.2 isaki {
146 1.2 isaki const aint_t *s;
147 1.2 isaki uint8_t *d;
148 1.2 isaki u_int sample_count;
149 1.2 isaki u_int i;
150 1.2 isaki
151 1.2 isaki DIAGNOSTIC_filter_arg(arg);
152 1.2 isaki KASSERT(arg->dstfmt->encoding == AUDIO_ENCODING_ALAW);
153 1.2 isaki KASSERT(arg->dstfmt->stride == 8);
154 1.2 isaki KASSERT(arg->dstfmt->precision == 8);
155 1.2 isaki KASSERT(audio_format2_is_internal(arg->srcfmt));
156 1.2 isaki KASSERT(arg->srcfmt->channels == arg->dstfmt->channels);
157 1.2 isaki
158 1.2 isaki s = arg->src;
159 1.2 isaki d = arg->dst;
160 1.2 isaki sample_count = arg->count * arg->srcfmt->channels;
161 1.2 isaki
162 1.2 isaki for (i = 0; i < sample_count; i++) {
163 1.2 isaki uint8_t val;
164 1.2 isaki val = (*s++) >> (AUDIO_INTERNAL_BITS - 8);
165 1.2 isaki *d++ = slinear8_to_alaw[val];
166 1.2 isaki }
167 1.2 isaki }
168