summaryrefslogtreecommitdiff
path: root/libTVaudio/audio/android_out.cpp (plain)
blob: fa0e519d5cf6cd52361efa172a3ca006f2301b44
1#define LOG_TAG "android_out"
2
3#include <stdio.h>
4#include <string.h>
5#include <stdlib.h>
6#include <pthread.h>
7#include <fcntl.h>
8#include <errno.h>
9#include <strings.h>
10#include <sys/ioctl.h>
11#include <cutils/log.h>
12#include <cutils/properties.h>
13#include <media/AudioTrack.h>
14
15#include "audio_usb_check.h"
16#include "android_out.h"
17#include "aml_audio.h"
18#include "DDP_media_source.h"
19
20using namespace android;
21
22static AudioTrack *glpTracker = NULL;
23static AudioTrack *glpTracker_raw = NULL;
24
25static sp<AudioTrack> gmpAudioTracker;
26static sp<AudioTrack> gmpAudioTracker_raw;
27
28extern struct circle_buffer android_out_buffer;
29extern struct circle_buffer DDP_out_buffer;
30extern struct circle_buffer DD_out_buffer;
31extern int output_record_enable;
32extern int spdif_audio_type;
33
34int I2S_state = 0;
35static int raw_start_flag = 0;
36static int mute_raw_data_size = 0;
37static audio_format_t last_aformat = AUDIO_FORMAT_AC3;
38//static int last_raw_flag = 0;
39static int RawAudioTrackRelease(void);
40static int RawAudioTrackInit(audio_format_t aformat,int sr);
41static int amsysfs_set_sysfs_int(const char *path, int val) {
42 int fd;
43 int bytes;
44 char bcmd[16];
45 fd = open(path, O_CREAT | O_RDWR | O_TRUNC, 0644);
46 if (fd >= 0) {
47 sprintf(bcmd, "%d", val);
48 bytes = write(fd, bcmd, strlen(bcmd));
49 close(fd);
50 return 0;
51 } else {
52 ALOGE("unable to open file %s,err: %s", path, strerror(errno));
53 }
54 return -1;
55}
56
57int amsysfs_get_sysfs_int(const char *path) {
58 int fd;
59 int val = 0;
60 char bcmd[16];
61 fd = open(path, O_RDONLY);
62 if (fd >= 0) {
63 read(fd, bcmd, sizeof(bcmd));
64 val = strtol(bcmd, NULL, 10);
65 close(fd);
66 }else {
67 ALOGE("unable to open file %s,err: %s", path, strerror(errno));
68 }
69 return val;
70}
71static void RawAudioTrackCallback(int event, void* user, void *info) {
72 AudioTrack::Buffer *buffer = static_cast<AudioTrack::Buffer *>(info);
73 int bytes_raw = 0;
74 if (event != AudioTrack::EVENT_MORE_DATA) {
75 ALOGD("%s, audio track envent = %d!\n", __FUNCTION__, event);
76 return;
77 }
78 if (buffer == NULL || buffer->size == 0) {
79 return;
80 }
81 bytes_raw = buffer_read(&DD_out_buffer,(char *) buffer->raw,
82 buffer->size);
83 //ALOGI("raw read got %d\n",bytes_raw);
84 if ( bytes_raw > 0) {
85 buffer->size = bytes_raw;
86 }
87 else
88 buffer->size = 0;
89 if (buffer->size > 0 && mute_raw_data_size < 32*1024) {
90 memset((char *)(buffer->i16),0,buffer->size);
91 mute_raw_data_size += buffer->size;
92 }
93 return;
94}
95static void AudioTrackCallback(int event, void* user, void *info) {
96 AudioTrack::Buffer *buffer = static_cast<AudioTrack::Buffer *>(info);
97
98 if (event != AudioTrack::EVENT_MORE_DATA) {
99 ALOGD("%s, audio track envent = %d!\n", __FUNCTION__, event);
100 return;
101 }
102 if (buffer == NULL || buffer->size == 0) {
103 return;
104 }
105 int bytes = 0;
106
107// code for raw data start
108 audio_format_t aformat = AUDIO_FORMAT_INVALID;
109 int user_raw_enable = amsysfs_get_sysfs_int("/sys/class/audiodsp/digital_raw");
110 //ALOGI("afmat %x,spdif_audio_type %x\n",aformat,spdif_audio_type);
111 int ddp_passth = (user_raw_enable == 2)&&(spdif_audio_type == EAC3);
112 if (user_raw_enable) {
113 if (ddp_passth) {
114 aformat = AUDIO_FORMAT_E_AC3;
115 }
116 else if (spdif_audio_type == AC3 || spdif_audio_type == EAC3 ) {
117 aformat = AUDIO_FORMAT_AC3;
118 }
119 else if (spdif_audio_type == DTS) {
120 aformat = AUDIO_FORMAT_DTS;
121 }
122 else if (spdif_audio_type == LPCM && last_aformat != AUDIO_FORMAT_INVALID) {
123 RawAudioTrackRelease();
124 }
125
126 if (aformat != last_aformat && aformat != AUDIO_FORMAT_INVALID) {
127 ALOGI("raw aformat changed from %x to %x\n",last_aformat,aformat);
128 RawAudioTrackRelease();
129 if (RawAudioTrackInit(aformat,48000/*TODO*/)) {
130 ALOGE("RawAudioTrackInit failed\n");
131 return;
132 }
133 }
134 }
135// raw data end
136 if (GetOutputdevice() == MODEANDROID) { // output PCM output when PCM data in
137//raw data start
138 RawAudioTrackRelease();
139// raw data end
140 bytes = buffer_read(&android_out_buffer, (char *) buffer->raw,
141 buffer->size);
142 if (bytes < 0)
143 buffer->size = 0;
144 } else if (GetOutputdevice() == MODERAW) {
145//raw data start
146 if (user_raw_enable == 0) {
147 RawAudioTrackRelease();
148 }
149// raw date end
150 bytes = buffer_read(&DDP_out_buffer, (char *) buffer->raw,
151 buffer->size);
152 if (bytes < 0)
153 buffer->size = 0;
154 } else {
155 if (output_record_enable == 1) {
156 bytes = buffer_read(&android_out_buffer, (char *) buffer->raw,
157 buffer->size);
158 if (bytes < 0)
159 buffer->size = 0;
160 } else {
161 memset(buffer->i16, 0, buffer->size);
162 }
163 }
164
165 I2S_state += 1;
166 return;
167}
168static int RawAudioTrackRelease(void) {
169 //raw here
170 if (glpTracker_raw != NULL ) {
171 if (raw_start_flag == 1)
172 glpTracker_raw->stop();
173 raw_start_flag = 0;
174 glpTracker_raw = NULL;
175 }
176 if (gmpAudioTracker_raw != NULL ) {
177 gmpAudioTracker_raw.clear();
178 gmpAudioTracker_raw = NULL;
179 ALOGI("RawAudioTrackRelease done\n");
180 }
181
182 // raw end
183#if 0
184 if (last_raw_flag == 2) {
185 ALOGI("change back digital raw to 2 for hdmi pass through\n");
186 amsysfs_set_sysfs_int("/sys/class/audiodsp/digital_raw",2);
187 last_raw_flag = 0;
188 }
189#endif
190 last_aformat = AUDIO_FORMAT_INVALID;
191 return 0;
192}
193static int AudioTrackRelease(void) {
194 if (glpTracker != NULL ) {
195 glpTracker->stop();
196 glpTracker = NULL;
197 }
198
199 if (gmpAudioTracker != NULL ) {
200 gmpAudioTracker.clear();
201 gmpAudioTracker = NULL;
202 }
203
204 return 0;
205}
206static int RawAudioTrackInit(audio_format_t aformat,int sr)
207{
208 status_t Status;
209 int user_raw_enable = amsysfs_get_sysfs_int("/sys/class/audiodsp/digital_raw");
210 int ddp_passth = (user_raw_enable == 2)&&(spdif_audio_type == EAC3);
211 int ret;
212
213 ALOGD("%s, entering...,aformat %x,sr %d\n", __FUNCTION__,aformat,sr);
214 //raw here
215 if (glpTracker_raw != NULL && gmpAudioTracker != NULL) {
216 glpTracker_raw = gmpAudioTracker_raw.get();
217 } else {
218 gmpAudioTracker_raw = new AudioTrack();
219 if (gmpAudioTracker_raw == NULL) {
220 ALOGE("%s, new gmpAudioTracker_raw failed.\n", __FUNCTION__);
221 return -1;
222 }
223 glpTracker_raw = gmpAudioTracker_raw.get();
224 }
225
226 Status = glpTracker_raw->set(AUDIO_STREAM_MUSIC, sr, aformat,
227 AUDIO_CHANNEL_OUT_STEREO, 0,
228 (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_DIRECT
229 | AUDIO_OUTPUT_FLAG_IEC958_NONAUDIO),
230 RawAudioTrackCallback, NULL,
231 0, 0, false, (audio_session_t)0);
232 if (Status != NO_ERROR) {
233 ALOGE("%s, AudioTrack raw set failed.\n", __FUNCTION__);
234 if (gmpAudioTracker_raw != NULL ) {
235 gmpAudioTracker_raw.clear();
236 glpTracker_raw = NULL;
237 }
238 return -1;
239 }
240 Status = glpTracker_raw->initCheck();
241 if (Status != NO_ERROR) {
242 ALOGE("%s, AudioTrack raw initCheck failed.\n", __FUNCTION__);
243 RawAudioTrackRelease();
244 return -1;
245 }
246 //raw end
247#if 0
248 int digital_raw = amsysfs_get_sysfs_int("/sys/class/audiodsp/digital_raw");
249 if (digital_raw == 2) {
250 ALOGI("change digital raw to 2 for spdif pass through\n");
251 amsysfs_set_sysfs_int("/sys/class/audiodsp/digital_raw",1);
252 last_raw_flag = 2;
253 }
254#endif
255 glpTracker_raw->start();
256 ALOGI("RawAudioTrackInit done\n");
257 last_aformat = aformat;
258 mute_raw_data_size = 0;
259 return 0;
260}
261static int AudioTrackInit(void) {
262 status_t Status;
263
264 ALOGD("%s, entering...\n", __FUNCTION__);
265
266 I2S_state = 0;
267
268 if (glpTracker != NULL && gmpAudioTracker != NULL) {
269 glpTracker = gmpAudioTracker.get();
270 } else {
271 gmpAudioTracker = new AudioTrack();
272 if (gmpAudioTracker == NULL) {
273 ALOGE("%s, new AudioTrack failed.\n", __FUNCTION__);
274 return -1;
275 }
276 glpTracker = gmpAudioTracker.get();
277 }
278
279 Status = glpTracker->set(AUDIO_STREAM_MUSIC, 48000, AUDIO_FORMAT_PCM_16_BIT,
280 AUDIO_CHANNEL_OUT_STEREO, 0, AUDIO_OUTPUT_FLAG_NONE,
281 AudioTrackCallback, NULL, 0, 0, false, (audio_session_t)0);
282
283 if (Status != NO_ERROR) {
284 ALOGE("%s, AudioTrack set failed.\n", __FUNCTION__);
285 if (gmpAudioTracker != NULL ) {
286 gmpAudioTracker.clear();
287 glpTracker = NULL;
288 }
289 return -1;
290 }
291
292 Status = glpTracker->initCheck();
293 if (Status != NO_ERROR) {
294 ALOGE("%s, AudioTrack initCheck failed.\n", __FUNCTION__);
295 AudioTrackRelease();
296 return -1;
297 }
298
299 glpTracker->start();
300
301 Status = glpTracker->setVolume(1.0, 1.0);
302 if (Status != NO_ERROR) {
303 ALOGE("%s, AudioTrack setVolume failed.\n", __FUNCTION__);
304 AudioTrackRelease();
305 return -1;
306 }
307 ALOGD("%s, exit...\n", __FUNCTION__);
308 return 0;//RawAudioTrackInit(AUDIO_FORMAT_AC3,48000);
309}
310
311int new_android_audiotrack(void) {
312 return AudioTrackInit();
313}
314
315int release_android_audiotrack(void) {
316 amsysfs_set_sysfs_int("/sys/class/audiodsp/digital_codec",0);
317 return AudioTrackRelease();
318}
319
320int release_raw_audio_track(void) {
321 amsysfs_set_sysfs_int("/sys/class/audiodsp/digital_codec", 0);
322 return RawAudioTrackRelease();
323}
324