IAudioFlinger.cpp revision 7df8c0b799d8f52d6386e03313286dbd7d5cdc7c
1/*
2**
3** Copyright 2007, The Android Open Source Project
4**
5** Licensed under the Apache License, Version 2.0 (the "License");
6** you may not use this file except in compliance with the License.
7** You may obtain a copy of the License at
8**
9**     http://www.apache.org/licenses/LICENSE-2.0
10**
11** Unless required by applicable law or agreed to in writing, software
12** distributed under the License is distributed on an "AS IS" BASIS,
13** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14** See the License for the specific language governing permissions and
15** limitations under the License.
16*/
17
18#define LOG_TAG "IAudioFlinger"
19//#define LOG_NDEBUG 0
20#include <utils/Log.h>
21
22#include <stdint.h>
23#include <sys/types.h>
24
25#include <binder/Parcel.h>
26
27#include <media/IAudioFlinger.h>
28
29namespace android {
30
31enum {
32    CREATE_TRACK = IBinder::FIRST_CALL_TRANSACTION,
33    OPEN_RECORD,
34    SAMPLE_RATE,
35    RESERVED,   // obsolete, was CHANNEL_COUNT
36    FORMAT,
37    FRAME_COUNT,
38    LATENCY,
39    SET_MASTER_VOLUME,
40    SET_MASTER_MUTE,
41    MASTER_VOLUME,
42    MASTER_MUTE,
43    SET_STREAM_VOLUME,
44    SET_STREAM_MUTE,
45    STREAM_VOLUME,
46    STREAM_MUTE,
47    SET_MODE,
48    SET_MIC_MUTE,
49    GET_MIC_MUTE,
50    SET_PARAMETERS,
51    GET_PARAMETERS,
52    REGISTER_CLIENT,
53    GET_INPUTBUFFERSIZE,
54    OPEN_OUTPUT,
55    OPEN_DUPLICATE_OUTPUT,
56    CLOSE_OUTPUT,
57    SUSPEND_OUTPUT,
58    RESTORE_OUTPUT,
59    OPEN_INPUT,
60    CLOSE_INPUT,
61    INVALIDATE_STREAM,
62    SET_VOICE_VOLUME,
63    GET_RENDER_POSITION,
64    GET_INPUT_FRAMES_LOST,
65    NEW_AUDIO_SESSION_ID,
66    ACQUIRE_AUDIO_SESSION_ID,
67    RELEASE_AUDIO_SESSION_ID,
68    QUERY_NUM_EFFECTS,
69    QUERY_EFFECT,
70    GET_EFFECT_DESCRIPTOR,
71    CREATE_EFFECT,
72    MOVE_EFFECTS,
73    LOAD_HW_MODULE,
74    GET_PRIMARY_OUTPUT_SAMPLING_RATE,
75    GET_PRIMARY_OUTPUT_FRAME_COUNT,
76    SET_LOW_RAM_DEVICE,
77    LIST_AUDIO_PORTS,
78    GET_AUDIO_PORT,
79    CREATE_AUDIO_PATCH,
80    RELEASE_AUDIO_PATCH,
81    LIST_AUDIO_PATCHES,
82    SET_AUDIO_PORT_CONFIG
83};
84
85class BpAudioFlinger : public BpInterface<IAudioFlinger>
86{
87public:
88    BpAudioFlinger(const sp<IBinder>& impl)
89        : BpInterface<IAudioFlinger>(impl)
90    {
91    }
92
93    virtual sp<IAudioTrack> createTrack(
94                                audio_stream_type_t streamType,
95                                uint32_t sampleRate,
96                                audio_format_t format,
97                                audio_channel_mask_t channelMask,
98                                size_t *pFrameCount,
99                                track_flags_t *flags,
100                                const sp<IMemory>& sharedBuffer,
101                                audio_io_handle_t output,
102                                pid_t tid,
103                                int *sessionId,
104                                int clientUid,
105                                status_t *status)
106    {
107        Parcel data, reply;
108        sp<IAudioTrack> track;
109        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
110        data.writeInt32((int32_t) streamType);
111        data.writeInt32(sampleRate);
112        data.writeInt32(format);
113        data.writeInt32(channelMask);
114        size_t frameCount = pFrameCount != NULL ? *pFrameCount : 0;
115        data.writeInt64(frameCount);
116        track_flags_t lFlags = flags != NULL ? *flags : (track_flags_t) TRACK_DEFAULT;
117        data.writeInt32(lFlags);
118        // haveSharedBuffer
119        if (sharedBuffer != 0) {
120            data.writeInt32(true);
121            data.writeStrongBinder(sharedBuffer->asBinder());
122        } else {
123            data.writeInt32(false);
124        }
125        data.writeInt32((int32_t) output);
126        data.writeInt32((int32_t) tid);
127        int lSessionId = AUDIO_SESSION_ALLOCATE;
128        if (sessionId != NULL) {
129            lSessionId = *sessionId;
130        }
131        data.writeInt32(lSessionId);
132        data.writeInt32(clientUid);
133        status_t lStatus = remote()->transact(CREATE_TRACK, data, &reply);
134        if (lStatus != NO_ERROR) {
135            ALOGE("createTrack error: %s", strerror(-lStatus));
136        } else {
137            frameCount = reply.readInt64();
138            if (pFrameCount != NULL) {
139                *pFrameCount = frameCount;
140            }
141            lFlags = reply.readInt32();
142            if (flags != NULL) {
143                *flags = lFlags;
144            }
145            lSessionId = reply.readInt32();
146            if (sessionId != NULL) {
147                *sessionId = lSessionId;
148            }
149            lStatus = reply.readInt32();
150            track = interface_cast<IAudioTrack>(reply.readStrongBinder());
151            if (lStatus == NO_ERROR) {
152                if (track == 0) {
153                    ALOGE("createTrack should have returned an IAudioTrack");
154                    lStatus = UNKNOWN_ERROR;
155                }
156            } else {
157                if (track != 0) {
158                    ALOGE("createTrack returned an IAudioTrack but with status %d", lStatus);
159                    track.clear();
160                }
161            }
162        }
163        if (status != NULL) {
164            *status = lStatus;
165        }
166        return track;
167    }
168
169    virtual sp<IAudioRecord> openRecord(
170                                audio_io_handle_t input,
171                                uint32_t sampleRate,
172                                audio_format_t format,
173                                audio_channel_mask_t channelMask,
174                                size_t *pFrameCount,
175                                track_flags_t *flags,
176                                pid_t tid,
177                                int *sessionId,
178                                size_t *notificationFrames,
179                                sp<IMemory>& cblk,
180                                sp<IMemory>& buffers,
181                                status_t *status)
182    {
183        Parcel data, reply;
184        sp<IAudioRecord> record;
185        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
186        data.writeInt32((int32_t) input);
187        data.writeInt32(sampleRate);
188        data.writeInt32(format);
189        data.writeInt32(channelMask);
190        size_t frameCount = pFrameCount != NULL ? *pFrameCount : 0;
191        data.writeInt64(frameCount);
192        track_flags_t lFlags = flags != NULL ? *flags : (track_flags_t) TRACK_DEFAULT;
193        data.writeInt32(lFlags);
194        data.writeInt32((int32_t) tid);
195        int lSessionId = AUDIO_SESSION_ALLOCATE;
196        if (sessionId != NULL) {
197            lSessionId = *sessionId;
198        }
199        data.writeInt32(lSessionId);
200        cblk.clear();
201        buffers.clear();
202        status_t lStatus = remote()->transact(OPEN_RECORD, data, &reply);
203        if (lStatus != NO_ERROR) {
204            ALOGE("openRecord error: %s", strerror(-lStatus));
205        } else {
206            frameCount = reply.readInt64();
207            if (pFrameCount != NULL) {
208                *pFrameCount = frameCount;
209            }
210            lFlags = reply.readInt32();
211            if (flags != NULL) {
212                *flags = lFlags;
213            }
214            lSessionId = reply.readInt32();
215            if (sessionId != NULL) {
216                *sessionId = lSessionId;
217            }
218            size_t lNotificationFrames = (size_t) reply.readInt64();
219            if (notificationFrames != NULL) {
220                *notificationFrames = lNotificationFrames;
221            }
222            lStatus = reply.readInt32();
223            record = interface_cast<IAudioRecord>(reply.readStrongBinder());
224            cblk = interface_cast<IMemory>(reply.readStrongBinder());
225            if (cblk != 0 && cblk->pointer() == NULL) {
226                cblk.clear();
227            }
228            buffers = interface_cast<IMemory>(reply.readStrongBinder());
229            if (buffers != 0 && buffers->pointer() == NULL) {
230                buffers.clear();
231            }
232            if (lStatus == NO_ERROR) {
233                if (record == 0) {
234                    ALOGE("openRecord should have returned an IAudioRecord");
235                    lStatus = UNKNOWN_ERROR;
236                } else if (cblk == 0) {
237                    ALOGE("openRecord should have returned a cblk");
238                    lStatus = NO_MEMORY;
239                }
240                // buffers is permitted to be 0
241            } else {
242                if (record != 0 || cblk != 0 || buffers != 0) {
243                    ALOGE("openRecord returned an IAudioRecord, cblk, "
244                          "or buffers but with status %d", lStatus);
245                }
246            }
247            if (lStatus != NO_ERROR) {
248                record.clear();
249                cblk.clear();
250                buffers.clear();
251            }
252        }
253        if (status != NULL) {
254            *status = lStatus;
255        }
256        return record;
257    }
258
259    virtual uint32_t sampleRate(audio_io_handle_t output) const
260    {
261        Parcel data, reply;
262        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
263        data.writeInt32((int32_t) output);
264        remote()->transact(SAMPLE_RATE, data, &reply);
265        return reply.readInt32();
266    }
267
268    virtual audio_format_t format(audio_io_handle_t output) const
269    {
270        Parcel data, reply;
271        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
272        data.writeInt32((int32_t) output);
273        remote()->transact(FORMAT, data, &reply);
274        return (audio_format_t) reply.readInt32();
275    }
276
277    virtual size_t frameCount(audio_io_handle_t output) const
278    {
279        Parcel data, reply;
280        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
281        data.writeInt32((int32_t) output);
282        remote()->transact(FRAME_COUNT, data, &reply);
283        return reply.readInt64();
284    }
285
286    virtual uint32_t latency(audio_io_handle_t output) const
287    {
288        Parcel data, reply;
289        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
290        data.writeInt32((int32_t) output);
291        remote()->transact(LATENCY, data, &reply);
292        return reply.readInt32();
293    }
294
295    virtual status_t setMasterVolume(float value)
296    {
297        Parcel data, reply;
298        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
299        data.writeFloat(value);
300        remote()->transact(SET_MASTER_VOLUME, data, &reply);
301        return reply.readInt32();
302    }
303
304    virtual status_t setMasterMute(bool muted)
305    {
306        Parcel data, reply;
307        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
308        data.writeInt32(muted);
309        remote()->transact(SET_MASTER_MUTE, data, &reply);
310        return reply.readInt32();
311    }
312
313    virtual float masterVolume() const
314    {
315        Parcel data, reply;
316        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
317        remote()->transact(MASTER_VOLUME, data, &reply);
318        return reply.readFloat();
319    }
320
321    virtual bool masterMute() const
322    {
323        Parcel data, reply;
324        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
325        remote()->transact(MASTER_MUTE, data, &reply);
326        return reply.readInt32();
327    }
328
329    virtual status_t setStreamVolume(audio_stream_type_t stream, float value,
330            audio_io_handle_t output)
331    {
332        Parcel data, reply;
333        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
334        data.writeInt32((int32_t) stream);
335        data.writeFloat(value);
336        data.writeInt32((int32_t) output);
337        remote()->transact(SET_STREAM_VOLUME, data, &reply);
338        return reply.readInt32();
339    }
340
341    virtual status_t setStreamMute(audio_stream_type_t stream, bool muted)
342    {
343        Parcel data, reply;
344        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
345        data.writeInt32((int32_t) stream);
346        data.writeInt32(muted);
347        remote()->transact(SET_STREAM_MUTE, data, &reply);
348        return reply.readInt32();
349    }
350
351    virtual float streamVolume(audio_stream_type_t stream, audio_io_handle_t output) const
352    {
353        Parcel data, reply;
354        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
355        data.writeInt32((int32_t) stream);
356        data.writeInt32((int32_t) output);
357        remote()->transact(STREAM_VOLUME, data, &reply);
358        return reply.readFloat();
359    }
360
361    virtual bool streamMute(audio_stream_type_t stream) const
362    {
363        Parcel data, reply;
364        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
365        data.writeInt32((int32_t) stream);
366        remote()->transact(STREAM_MUTE, data, &reply);
367        return reply.readInt32();
368    }
369
370    virtual status_t setMode(audio_mode_t mode)
371    {
372        Parcel data, reply;
373        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
374        data.writeInt32(mode);
375        remote()->transact(SET_MODE, data, &reply);
376        return reply.readInt32();
377    }
378
379    virtual status_t setMicMute(bool state)
380    {
381        Parcel data, reply;
382        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
383        data.writeInt32(state);
384        remote()->transact(SET_MIC_MUTE, data, &reply);
385        return reply.readInt32();
386    }
387
388    virtual bool getMicMute() const
389    {
390        Parcel data, reply;
391        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
392        remote()->transact(GET_MIC_MUTE, data, &reply);
393        return reply.readInt32();
394    }
395
396    virtual status_t setParameters(audio_io_handle_t ioHandle, const String8& keyValuePairs)
397    {
398        Parcel data, reply;
399        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
400        data.writeInt32((int32_t) ioHandle);
401        data.writeString8(keyValuePairs);
402        remote()->transact(SET_PARAMETERS, data, &reply);
403        return reply.readInt32();
404    }
405
406    virtual String8 getParameters(audio_io_handle_t ioHandle, const String8& keys) const
407    {
408        Parcel data, reply;
409        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
410        data.writeInt32((int32_t) ioHandle);
411        data.writeString8(keys);
412        remote()->transact(GET_PARAMETERS, data, &reply);
413        return reply.readString8();
414    }
415
416    virtual void registerClient(const sp<IAudioFlingerClient>& client)
417    {
418        Parcel data, reply;
419        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
420        data.writeStrongBinder(client->asBinder());
421        remote()->transact(REGISTER_CLIENT, data, &reply);
422    }
423
424    virtual size_t getInputBufferSize(uint32_t sampleRate, audio_format_t format,
425            audio_channel_mask_t channelMask) const
426    {
427        Parcel data, reply;
428        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
429        data.writeInt32(sampleRate);
430        data.writeInt32(format);
431        data.writeInt32(channelMask);
432        remote()->transact(GET_INPUTBUFFERSIZE, data, &reply);
433        return reply.readInt64();
434    }
435
436    virtual audio_io_handle_t openOutput(audio_module_handle_t module,
437                                         audio_devices_t *pDevices,
438                                         uint32_t *pSamplingRate,
439                                         audio_format_t *pFormat,
440                                         audio_channel_mask_t *pChannelMask,
441                                         uint32_t *pLatencyMs,
442                                         audio_output_flags_t flags,
443                                         const audio_offload_info_t *offloadInfo)
444    {
445        Parcel data, reply;
446        audio_devices_t devices = pDevices != NULL ? *pDevices : AUDIO_DEVICE_NONE;
447        uint32_t samplingRate = pSamplingRate != NULL ? *pSamplingRate : 0;
448        audio_format_t format = pFormat != NULL ? *pFormat : AUDIO_FORMAT_DEFAULT;
449        audio_channel_mask_t channelMask = pChannelMask != NULL ?
450                *pChannelMask : (audio_channel_mask_t)0;
451        uint32_t latency = pLatencyMs != NULL ? *pLatencyMs : 0;
452        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
453        data.writeInt32(module);
454        data.writeInt32(devices);
455        data.writeInt32(samplingRate);
456        data.writeInt32(format);
457        data.writeInt32(channelMask);
458        data.writeInt32(latency);
459        data.writeInt32((int32_t) flags);
460        // hasOffloadInfo
461        if (offloadInfo == NULL) {
462            data.writeInt32(0);
463        } else {
464            data.writeInt32(1);
465            data.write(offloadInfo, sizeof(audio_offload_info_t));
466        }
467        remote()->transact(OPEN_OUTPUT, data, &reply);
468        audio_io_handle_t output = (audio_io_handle_t) reply.readInt32();
469        ALOGV("openOutput() returned output, %d", output);
470        devices = (audio_devices_t)reply.readInt32();
471        if (pDevices != NULL) {
472            *pDevices = devices;
473        }
474        samplingRate = reply.readInt32();
475        if (pSamplingRate != NULL) {
476            *pSamplingRate = samplingRate;
477        }
478        format = (audio_format_t) reply.readInt32();
479        if (pFormat != NULL) {
480            *pFormat = format;
481        }
482        channelMask = (audio_channel_mask_t)reply.readInt32();
483        if (pChannelMask != NULL) {
484            *pChannelMask = channelMask;
485        }
486        latency = reply.readInt32();
487        if (pLatencyMs != NULL) {
488            *pLatencyMs = latency;
489        }
490        return output;
491    }
492
493    virtual audio_io_handle_t openDuplicateOutput(audio_io_handle_t output1,
494            audio_io_handle_t output2)
495    {
496        Parcel data, reply;
497        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
498        data.writeInt32((int32_t) output1);
499        data.writeInt32((int32_t) output2);
500        remote()->transact(OPEN_DUPLICATE_OUTPUT, data, &reply);
501        return (audio_io_handle_t) reply.readInt32();
502    }
503
504    virtual status_t closeOutput(audio_io_handle_t output)
505    {
506        Parcel data, reply;
507        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
508        data.writeInt32((int32_t) output);
509        remote()->transact(CLOSE_OUTPUT, data, &reply);
510        return reply.readInt32();
511    }
512
513    virtual status_t suspendOutput(audio_io_handle_t output)
514    {
515        Parcel data, reply;
516        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
517        data.writeInt32((int32_t) output);
518        remote()->transact(SUSPEND_OUTPUT, data, &reply);
519        return reply.readInt32();
520    }
521
522    virtual status_t restoreOutput(audio_io_handle_t output)
523    {
524        Parcel data, reply;
525        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
526        data.writeInt32((int32_t) output);
527        remote()->transact(RESTORE_OUTPUT, data, &reply);
528        return reply.readInt32();
529    }
530
531    virtual audio_io_handle_t openInput(audio_module_handle_t module,
532                                        audio_devices_t *pDevices,
533                                        uint32_t *pSamplingRate,
534                                        audio_format_t *pFormat,
535                                        audio_channel_mask_t *pChannelMask)
536    {
537        Parcel data, reply;
538        audio_devices_t devices = pDevices != NULL ? *pDevices : AUDIO_DEVICE_NONE;
539        uint32_t samplingRate = pSamplingRate != NULL ? *pSamplingRate : 0;
540        audio_format_t format = pFormat != NULL ? *pFormat : AUDIO_FORMAT_DEFAULT;
541        audio_channel_mask_t channelMask = pChannelMask != NULL ?
542                *pChannelMask : (audio_channel_mask_t)0;
543
544        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
545        data.writeInt32(module);
546        data.writeInt32(devices);
547        data.writeInt32(samplingRate);
548        data.writeInt32(format);
549        data.writeInt32(channelMask);
550        remote()->transact(OPEN_INPUT, data, &reply);
551        audio_io_handle_t input = (audio_io_handle_t) reply.readInt32();
552        devices = (audio_devices_t)reply.readInt32();
553        if (pDevices != NULL) {
554            *pDevices = devices;
555        }
556        samplingRate = reply.readInt32();
557        if (pSamplingRate != NULL) {
558            *pSamplingRate = samplingRate;
559        }
560        format = (audio_format_t) reply.readInt32();
561        if (pFormat != NULL) {
562            *pFormat = format;
563        }
564        channelMask = (audio_channel_mask_t)reply.readInt32();
565        if (pChannelMask != NULL) {
566            *pChannelMask = channelMask;
567        }
568        return input;
569    }
570
571    virtual status_t closeInput(int input)
572    {
573        Parcel data, reply;
574        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
575        data.writeInt32(input);
576        remote()->transact(CLOSE_INPUT, data, &reply);
577        return reply.readInt32();
578    }
579
580    virtual status_t invalidateStream(audio_stream_type_t stream)
581    {
582        Parcel data, reply;
583        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
584        data.writeInt32((int32_t) stream);
585        remote()->transact(INVALIDATE_STREAM, data, &reply);
586        return reply.readInt32();
587    }
588
589    virtual status_t setVoiceVolume(float volume)
590    {
591        Parcel data, reply;
592        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
593        data.writeFloat(volume);
594        remote()->transact(SET_VOICE_VOLUME, data, &reply);
595        return reply.readInt32();
596    }
597
598    virtual status_t getRenderPosition(uint32_t *halFrames, uint32_t *dspFrames,
599            audio_io_handle_t output) const
600    {
601        Parcel data, reply;
602        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
603        data.writeInt32((int32_t) output);
604        remote()->transact(GET_RENDER_POSITION, data, &reply);
605        status_t status = reply.readInt32();
606        if (status == NO_ERROR) {
607            uint32_t tmp = reply.readInt32();
608            if (halFrames != NULL) {
609                *halFrames = tmp;
610            }
611            tmp = reply.readInt32();
612            if (dspFrames != NULL) {
613                *dspFrames = tmp;
614            }
615        }
616        return status;
617    }
618
619    virtual uint32_t getInputFramesLost(audio_io_handle_t ioHandle) const
620    {
621        Parcel data, reply;
622        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
623        data.writeInt32((int32_t) ioHandle);
624        status_t status = remote()->transact(GET_INPUT_FRAMES_LOST, data, &reply);
625        if (status != NO_ERROR) {
626            return 0;
627        }
628        return (uint32_t) reply.readInt32();
629    }
630
631    virtual int newAudioSessionId()
632    {
633        Parcel data, reply;
634        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
635        status_t status = remote()->transact(NEW_AUDIO_SESSION_ID, data, &reply);
636        int id = AUDIO_SESSION_ALLOCATE;
637        if (status == NO_ERROR) {
638            id = reply.readInt32();
639        }
640        return id;
641    }
642
643    virtual void acquireAudioSessionId(int audioSession, int pid)
644    {
645        Parcel data, reply;
646        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
647        data.writeInt32(audioSession);
648        data.writeInt32(pid);
649        remote()->transact(ACQUIRE_AUDIO_SESSION_ID, data, &reply);
650    }
651
652    virtual void releaseAudioSessionId(int audioSession, int pid)
653    {
654        Parcel data, reply;
655        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
656        data.writeInt32(audioSession);
657        data.writeInt32(pid);
658        remote()->transact(RELEASE_AUDIO_SESSION_ID, data, &reply);
659    }
660
661    virtual status_t queryNumberEffects(uint32_t *numEffects) const
662    {
663        Parcel data, reply;
664        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
665        status_t status = remote()->transact(QUERY_NUM_EFFECTS, data, &reply);
666        if (status != NO_ERROR) {
667            return status;
668        }
669        status = reply.readInt32();
670        if (status != NO_ERROR) {
671            return status;
672        }
673        if (numEffects != NULL) {
674            *numEffects = (uint32_t)reply.readInt32();
675        }
676        return NO_ERROR;
677    }
678
679    virtual status_t queryEffect(uint32_t index, effect_descriptor_t *pDescriptor) const
680    {
681        if (pDescriptor == NULL) {
682            return BAD_VALUE;
683        }
684        Parcel data, reply;
685        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
686        data.writeInt32(index);
687        status_t status = remote()->transact(QUERY_EFFECT, data, &reply);
688        if (status != NO_ERROR) {
689            return status;
690        }
691        status = reply.readInt32();
692        if (status != NO_ERROR) {
693            return status;
694        }
695        reply.read(pDescriptor, sizeof(effect_descriptor_t));
696        return NO_ERROR;
697    }
698
699    virtual status_t getEffectDescriptor(const effect_uuid_t *pUuid,
700            effect_descriptor_t *pDescriptor) const
701    {
702        if (pUuid == NULL || pDescriptor == NULL) {
703            return BAD_VALUE;
704        }
705        Parcel data, reply;
706        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
707        data.write(pUuid, sizeof(effect_uuid_t));
708        status_t status = remote()->transact(GET_EFFECT_DESCRIPTOR, data, &reply);
709        if (status != NO_ERROR) {
710            return status;
711        }
712        status = reply.readInt32();
713        if (status != NO_ERROR) {
714            return status;
715        }
716        reply.read(pDescriptor, sizeof(effect_descriptor_t));
717        return NO_ERROR;
718    }
719
720    virtual sp<IEffect> createEffect(
721                                    effect_descriptor_t *pDesc,
722                                    const sp<IEffectClient>& client,
723                                    int32_t priority,
724                                    audio_io_handle_t output,
725                                    int sessionId,
726                                    status_t *status,
727                                    int *id,
728                                    int *enabled)
729    {
730        Parcel data, reply;
731        sp<IEffect> effect;
732
733        if (pDesc == NULL) {
734            return effect;
735            if (status != NULL) {
736                *status = BAD_VALUE;
737            }
738        }
739
740        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
741        data.write(pDesc, sizeof(effect_descriptor_t));
742        data.writeStrongBinder(client->asBinder());
743        data.writeInt32(priority);
744        data.writeInt32((int32_t) output);
745        data.writeInt32(sessionId);
746
747        status_t lStatus = remote()->transact(CREATE_EFFECT, data, &reply);
748        if (lStatus != NO_ERROR) {
749            ALOGE("createEffect error: %s", strerror(-lStatus));
750        } else {
751            lStatus = reply.readInt32();
752            int tmp = reply.readInt32();
753            if (id != NULL) {
754                *id = tmp;
755            }
756            tmp = reply.readInt32();
757            if (enabled != NULL) {
758                *enabled = tmp;
759            }
760            effect = interface_cast<IEffect>(reply.readStrongBinder());
761            reply.read(pDesc, sizeof(effect_descriptor_t));
762        }
763        if (status != NULL) {
764            *status = lStatus;
765        }
766
767        return effect;
768    }
769
770    virtual status_t moveEffects(int session, audio_io_handle_t srcOutput,
771            audio_io_handle_t dstOutput)
772    {
773        Parcel data, reply;
774        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
775        data.writeInt32(session);
776        data.writeInt32((int32_t) srcOutput);
777        data.writeInt32((int32_t) dstOutput);
778        remote()->transact(MOVE_EFFECTS, data, &reply);
779        return reply.readInt32();
780    }
781
782    virtual audio_module_handle_t loadHwModule(const char *name)
783    {
784        Parcel data, reply;
785        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
786        data.writeCString(name);
787        remote()->transact(LOAD_HW_MODULE, data, &reply);
788        return (audio_module_handle_t) reply.readInt32();
789    }
790
791    virtual uint32_t getPrimaryOutputSamplingRate()
792    {
793        Parcel data, reply;
794        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
795        remote()->transact(GET_PRIMARY_OUTPUT_SAMPLING_RATE, data, &reply);
796        return reply.readInt32();
797    }
798
799    virtual size_t getPrimaryOutputFrameCount()
800    {
801        Parcel data, reply;
802        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
803        remote()->transact(GET_PRIMARY_OUTPUT_FRAME_COUNT, data, &reply);
804        return reply.readInt64();
805    }
806
807    virtual status_t setLowRamDevice(bool isLowRamDevice)
808    {
809        Parcel data, reply;
810        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
811        data.writeInt32((int) isLowRamDevice);
812        remote()->transact(SET_LOW_RAM_DEVICE, data, &reply);
813        return reply.readInt32();
814    }
815    virtual status_t listAudioPorts(unsigned int *num_ports,
816                                    struct audio_port *ports)
817    {
818        if (num_ports == NULL || *num_ports == 0 || ports == NULL) {
819            return BAD_VALUE;
820        }
821        Parcel data, reply;
822        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
823        data.writeInt32(*num_ports);
824        status_t status = remote()->transact(LIST_AUDIO_PORTS, data, &reply);
825        if (status != NO_ERROR ||
826                (status = (status_t)reply.readInt32()) != NO_ERROR) {
827            return status;
828        }
829        *num_ports = (unsigned int)reply.readInt32();
830        reply.read(ports, *num_ports * sizeof(struct audio_port));
831        return status;
832    }
833    virtual status_t getAudioPort(struct audio_port *port)
834    {
835        if (port == NULL) {
836            return BAD_VALUE;
837        }
838        Parcel data, reply;
839        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
840        data.write(port, sizeof(struct audio_port));
841        status_t status = remote()->transact(GET_AUDIO_PORT, data, &reply);
842        if (status != NO_ERROR ||
843                (status = (status_t)reply.readInt32()) != NO_ERROR) {
844            return status;
845        }
846        reply.read(port, sizeof(struct audio_port));
847        return status;
848    }
849    virtual status_t createAudioPatch(const struct audio_patch *patch,
850                                       audio_patch_handle_t *handle)
851    {
852        if (patch == NULL || handle == NULL) {
853            return BAD_VALUE;
854        }
855        Parcel data, reply;
856        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
857        data.write(patch, sizeof(struct audio_patch));
858        data.write(handle, sizeof(audio_patch_handle_t));
859        status_t status = remote()->transact(CREATE_AUDIO_PATCH, data, &reply);
860        if (status != NO_ERROR ||
861                (status = (status_t)reply.readInt32()) != NO_ERROR) {
862            return status;
863        }
864        reply.read(handle, sizeof(audio_patch_handle_t));
865        return status;
866    }
867    virtual status_t releaseAudioPatch(audio_patch_handle_t handle)
868    {
869        Parcel data, reply;
870        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
871        data.write(&handle, sizeof(audio_patch_handle_t));
872        status_t status = remote()->transact(RELEASE_AUDIO_PATCH, data, &reply);
873        if (status != NO_ERROR) {
874            status = (status_t)reply.readInt32();
875        }
876        return status;
877    }
878    virtual status_t listAudioPatches(unsigned int *num_patches,
879                                      struct audio_patch *patches)
880    {
881        if (num_patches == NULL || *num_patches == 0 || patches == NULL) {
882            return BAD_VALUE;
883        }
884        Parcel data, reply;
885        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
886        data.writeInt32(*num_patches);
887        status_t status = remote()->transact(LIST_AUDIO_PATCHES, data, &reply);
888        if (status != NO_ERROR ||
889                (status = (status_t)reply.readInt32()) != NO_ERROR) {
890            return status;
891        }
892        *num_patches = (unsigned int)reply.readInt32();
893        reply.read(patches, *num_patches * sizeof(struct audio_patch));
894        return status;
895    }
896    virtual status_t setAudioPortConfig(const struct audio_port_config *config)
897    {
898        if (config == NULL) {
899            return BAD_VALUE;
900        }
901        Parcel data, reply;
902        data.writeInterfaceToken(IAudioFlinger::getInterfaceDescriptor());
903        data.write(config, sizeof(struct audio_port_config));
904        status_t status = remote()->transact(SET_AUDIO_PORT_CONFIG, data, &reply);
905        if (status != NO_ERROR) {
906            status = (status_t)reply.readInt32();
907        }
908        return status;
909    }
910};
911
912IMPLEMENT_META_INTERFACE(AudioFlinger, "android.media.IAudioFlinger");
913
914// ----------------------------------------------------------------------
915
916status_t BnAudioFlinger::onTransact(
917    uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
918{
919    switch (code) {
920        case CREATE_TRACK: {
921            CHECK_INTERFACE(IAudioFlinger, data, reply);
922            int streamType = data.readInt32();
923            uint32_t sampleRate = data.readInt32();
924            audio_format_t format = (audio_format_t) data.readInt32();
925            audio_channel_mask_t channelMask = data.readInt32();
926            size_t frameCount = data.readInt64();
927            track_flags_t flags = (track_flags_t) data.readInt32();
928            bool haveSharedBuffer = data.readInt32() != 0;
929            sp<IMemory> buffer;
930            if (haveSharedBuffer) {
931                buffer = interface_cast<IMemory>(data.readStrongBinder());
932            }
933            audio_io_handle_t output = (audio_io_handle_t) data.readInt32();
934            pid_t tid = (pid_t) data.readInt32();
935            int sessionId = data.readInt32();
936            int clientUid = data.readInt32();
937            status_t status;
938            sp<IAudioTrack> track;
939            if ((haveSharedBuffer && (buffer == 0)) ||
940                    ((buffer != 0) && (buffer->pointer() == NULL))) {
941                ALOGW("CREATE_TRACK: cannot retrieve shared memory");
942                status = DEAD_OBJECT;
943            } else {
944                track = createTrack(
945                        (audio_stream_type_t) streamType, sampleRate, format,
946                        channelMask, &frameCount, &flags, buffer, output, tid,
947                        &sessionId, clientUid, &status);
948                LOG_ALWAYS_FATAL_IF((track != 0) != (status == NO_ERROR));
949            }
950            reply->writeInt64(frameCount);
951            reply->writeInt32(flags);
952            reply->writeInt32(sessionId);
953            reply->writeInt32(status);
954            reply->writeStrongBinder(track->asBinder());
955            return NO_ERROR;
956        } break;
957        case OPEN_RECORD: {
958            CHECK_INTERFACE(IAudioFlinger, data, reply);
959            audio_io_handle_t input = (audio_io_handle_t) data.readInt32();
960            uint32_t sampleRate = data.readInt32();
961            audio_format_t format = (audio_format_t) data.readInt32();
962            audio_channel_mask_t channelMask = data.readInt32();
963            size_t frameCount = data.readInt64();
964            track_flags_t flags = (track_flags_t) data.readInt32();
965            pid_t tid = (pid_t) data.readInt32();
966            int sessionId = data.readInt32();
967            size_t notificationFrames = 0;
968            sp<IMemory> cblk;
969            sp<IMemory> buffers;
970            status_t status;
971            sp<IAudioRecord> record = openRecord(input,
972                    sampleRate, format, channelMask, &frameCount, &flags, tid, &sessionId,
973                    &notificationFrames,
974                    cblk, buffers, &status);
975            LOG_ALWAYS_FATAL_IF((record != 0) != (status == NO_ERROR));
976            reply->writeInt64(frameCount);
977            reply->writeInt32(flags);
978            reply->writeInt32(sessionId);
979            reply->writeInt64(notificationFrames);
980            reply->writeInt32(status);
981            reply->writeStrongBinder(record->asBinder());
982            reply->writeStrongBinder(cblk->asBinder());
983            reply->writeStrongBinder(buffers->asBinder());
984            return NO_ERROR;
985        } break;
986        case SAMPLE_RATE: {
987            CHECK_INTERFACE(IAudioFlinger, data, reply);
988            reply->writeInt32( sampleRate((audio_io_handle_t) data.readInt32()) );
989            return NO_ERROR;
990        } break;
991        case FORMAT: {
992            CHECK_INTERFACE(IAudioFlinger, data, reply);
993            reply->writeInt32( format((audio_io_handle_t) data.readInt32()) );
994            return NO_ERROR;
995        } break;
996        case FRAME_COUNT: {
997            CHECK_INTERFACE(IAudioFlinger, data, reply);
998            reply->writeInt64( frameCount((audio_io_handle_t) data.readInt32()) );
999            return NO_ERROR;
1000        } break;
1001        case LATENCY: {
1002            CHECK_INTERFACE(IAudioFlinger, data, reply);
1003            reply->writeInt32( latency((audio_io_handle_t) data.readInt32()) );
1004            return NO_ERROR;
1005        } break;
1006        case SET_MASTER_VOLUME: {
1007            CHECK_INTERFACE(IAudioFlinger, data, reply);
1008            reply->writeInt32( setMasterVolume(data.readFloat()) );
1009            return NO_ERROR;
1010        } break;
1011        case SET_MASTER_MUTE: {
1012            CHECK_INTERFACE(IAudioFlinger, data, reply);
1013            reply->writeInt32( setMasterMute(data.readInt32()) );
1014            return NO_ERROR;
1015        } break;
1016        case MASTER_VOLUME: {
1017            CHECK_INTERFACE(IAudioFlinger, data, reply);
1018            reply->writeFloat( masterVolume() );
1019            return NO_ERROR;
1020        } break;
1021        case MASTER_MUTE: {
1022            CHECK_INTERFACE(IAudioFlinger, data, reply);
1023            reply->writeInt32( masterMute() );
1024            return NO_ERROR;
1025        } break;
1026        case SET_STREAM_VOLUME: {
1027            CHECK_INTERFACE(IAudioFlinger, data, reply);
1028            int stream = data.readInt32();
1029            float volume = data.readFloat();
1030            audio_io_handle_t output = (audio_io_handle_t) data.readInt32();
1031            reply->writeInt32( setStreamVolume((audio_stream_type_t) stream, volume, output) );
1032            return NO_ERROR;
1033        } break;
1034        case SET_STREAM_MUTE: {
1035            CHECK_INTERFACE(IAudioFlinger, data, reply);
1036            int stream = data.readInt32();
1037            reply->writeInt32( setStreamMute((audio_stream_type_t) stream, data.readInt32()) );
1038            return NO_ERROR;
1039        } break;
1040        case STREAM_VOLUME: {
1041            CHECK_INTERFACE(IAudioFlinger, data, reply);
1042            int stream = data.readInt32();
1043            int output = data.readInt32();
1044            reply->writeFloat( streamVolume((audio_stream_type_t) stream, output) );
1045            return NO_ERROR;
1046        } break;
1047        case STREAM_MUTE: {
1048            CHECK_INTERFACE(IAudioFlinger, data, reply);
1049            int stream = data.readInt32();
1050            reply->writeInt32( streamMute((audio_stream_type_t) stream) );
1051            return NO_ERROR;
1052        } break;
1053        case SET_MODE: {
1054            CHECK_INTERFACE(IAudioFlinger, data, reply);
1055            audio_mode_t mode = (audio_mode_t) data.readInt32();
1056            reply->writeInt32( setMode(mode) );
1057            return NO_ERROR;
1058        } break;
1059        case SET_MIC_MUTE: {
1060            CHECK_INTERFACE(IAudioFlinger, data, reply);
1061            int state = data.readInt32();
1062            reply->writeInt32( setMicMute(state) );
1063            return NO_ERROR;
1064        } break;
1065        case GET_MIC_MUTE: {
1066            CHECK_INTERFACE(IAudioFlinger, data, reply);
1067            reply->writeInt32( getMicMute() );
1068            return NO_ERROR;
1069        } break;
1070        case SET_PARAMETERS: {
1071            CHECK_INTERFACE(IAudioFlinger, data, reply);
1072            audio_io_handle_t ioHandle = (audio_io_handle_t) data.readInt32();
1073            String8 keyValuePairs(data.readString8());
1074            reply->writeInt32(setParameters(ioHandle, keyValuePairs));
1075            return NO_ERROR;
1076        } break;
1077        case GET_PARAMETERS: {
1078            CHECK_INTERFACE(IAudioFlinger, data, reply);
1079            audio_io_handle_t ioHandle = (audio_io_handle_t) data.readInt32();
1080            String8 keys(data.readString8());
1081            reply->writeString8(getParameters(ioHandle, keys));
1082            return NO_ERROR;
1083        } break;
1084
1085        case REGISTER_CLIENT: {
1086            CHECK_INTERFACE(IAudioFlinger, data, reply);
1087            sp<IAudioFlingerClient> client = interface_cast<IAudioFlingerClient>(
1088                    data.readStrongBinder());
1089            registerClient(client);
1090            return NO_ERROR;
1091        } break;
1092        case GET_INPUTBUFFERSIZE: {
1093            CHECK_INTERFACE(IAudioFlinger, data, reply);
1094            uint32_t sampleRate = data.readInt32();
1095            audio_format_t format = (audio_format_t) data.readInt32();
1096            audio_channel_mask_t channelMask = data.readInt32();
1097            reply->writeInt64( getInputBufferSize(sampleRate, format, channelMask) );
1098            return NO_ERROR;
1099        } break;
1100        case OPEN_OUTPUT: {
1101            CHECK_INTERFACE(IAudioFlinger, data, reply);
1102            audio_module_handle_t module = (audio_module_handle_t)data.readInt32();
1103            audio_devices_t devices = (audio_devices_t)data.readInt32();
1104            uint32_t samplingRate = data.readInt32();
1105            audio_format_t format = (audio_format_t) data.readInt32();
1106            audio_channel_mask_t channelMask = (audio_channel_mask_t)data.readInt32();
1107            uint32_t latency = data.readInt32();
1108            audio_output_flags_t flags = (audio_output_flags_t) data.readInt32();
1109            bool hasOffloadInfo = data.readInt32() != 0;
1110            audio_offload_info_t offloadInfo;
1111            if (hasOffloadInfo) {
1112                data.read(&offloadInfo, sizeof(audio_offload_info_t));
1113            }
1114            audio_io_handle_t output = openOutput(module,
1115                                                 &devices,
1116                                                 &samplingRate,
1117                                                 &format,
1118                                                 &channelMask,
1119                                                 &latency,
1120                                                 flags,
1121                                                 hasOffloadInfo ? &offloadInfo : NULL);
1122            ALOGV("OPEN_OUTPUT output, %d", output);
1123            reply->writeInt32((int32_t) output);
1124            reply->writeInt32(devices);
1125            reply->writeInt32(samplingRate);
1126            reply->writeInt32(format);
1127            reply->writeInt32(channelMask);
1128            reply->writeInt32(latency);
1129            return NO_ERROR;
1130        } break;
1131        case OPEN_DUPLICATE_OUTPUT: {
1132            CHECK_INTERFACE(IAudioFlinger, data, reply);
1133            audio_io_handle_t output1 = (audio_io_handle_t) data.readInt32();
1134            audio_io_handle_t output2 = (audio_io_handle_t) data.readInt32();
1135            reply->writeInt32((int32_t) openDuplicateOutput(output1, output2));
1136            return NO_ERROR;
1137        } break;
1138        case CLOSE_OUTPUT: {
1139            CHECK_INTERFACE(IAudioFlinger, data, reply);
1140            reply->writeInt32(closeOutput((audio_io_handle_t) data.readInt32()));
1141            return NO_ERROR;
1142        } break;
1143        case SUSPEND_OUTPUT: {
1144            CHECK_INTERFACE(IAudioFlinger, data, reply);
1145            reply->writeInt32(suspendOutput((audio_io_handle_t) data.readInt32()));
1146            return NO_ERROR;
1147        } break;
1148        case RESTORE_OUTPUT: {
1149            CHECK_INTERFACE(IAudioFlinger, data, reply);
1150            reply->writeInt32(restoreOutput((audio_io_handle_t) data.readInt32()));
1151            return NO_ERROR;
1152        } break;
1153        case OPEN_INPUT: {
1154            CHECK_INTERFACE(IAudioFlinger, data, reply);
1155            audio_module_handle_t module = (audio_module_handle_t)data.readInt32();
1156            audio_devices_t devices = (audio_devices_t)data.readInt32();
1157            uint32_t samplingRate = data.readInt32();
1158            audio_format_t format = (audio_format_t) data.readInt32();
1159            audio_channel_mask_t channelMask = (audio_channel_mask_t)data.readInt32();
1160
1161            audio_io_handle_t input = openInput(module,
1162                                             &devices,
1163                                             &samplingRate,
1164                                             &format,
1165                                             &channelMask);
1166            reply->writeInt32((int32_t) input);
1167            reply->writeInt32(devices);
1168            reply->writeInt32(samplingRate);
1169            reply->writeInt32(format);
1170            reply->writeInt32(channelMask);
1171            return NO_ERROR;
1172        } break;
1173        case CLOSE_INPUT: {
1174            CHECK_INTERFACE(IAudioFlinger, data, reply);
1175            reply->writeInt32(closeInput((audio_io_handle_t) data.readInt32()));
1176            return NO_ERROR;
1177        } break;
1178        case INVALIDATE_STREAM: {
1179            CHECK_INTERFACE(IAudioFlinger, data, reply);
1180            audio_stream_type_t stream = (audio_stream_type_t) data.readInt32();
1181            reply->writeInt32(invalidateStream(stream));
1182            return NO_ERROR;
1183        } break;
1184        case SET_VOICE_VOLUME: {
1185            CHECK_INTERFACE(IAudioFlinger, data, reply);
1186            float volume = data.readFloat();
1187            reply->writeInt32( setVoiceVolume(volume) );
1188            return NO_ERROR;
1189        } break;
1190        case GET_RENDER_POSITION: {
1191            CHECK_INTERFACE(IAudioFlinger, data, reply);
1192            audio_io_handle_t output = (audio_io_handle_t) data.readInt32();
1193            uint32_t halFrames;
1194            uint32_t dspFrames;
1195            status_t status = getRenderPosition(&halFrames, &dspFrames, output);
1196            reply->writeInt32(status);
1197            if (status == NO_ERROR) {
1198                reply->writeInt32(halFrames);
1199                reply->writeInt32(dspFrames);
1200            }
1201            return NO_ERROR;
1202        }
1203        case GET_INPUT_FRAMES_LOST: {
1204            CHECK_INTERFACE(IAudioFlinger, data, reply);
1205            audio_io_handle_t ioHandle = (audio_io_handle_t) data.readInt32();
1206            reply->writeInt32((int32_t) getInputFramesLost(ioHandle));
1207            return NO_ERROR;
1208        } break;
1209        case NEW_AUDIO_SESSION_ID: {
1210            CHECK_INTERFACE(IAudioFlinger, data, reply);
1211            reply->writeInt32(newAudioSessionId());
1212            return NO_ERROR;
1213        } break;
1214        case ACQUIRE_AUDIO_SESSION_ID: {
1215            CHECK_INTERFACE(IAudioFlinger, data, reply);
1216            int audioSession = data.readInt32();
1217            int pid = data.readInt32();
1218            acquireAudioSessionId(audioSession, pid);
1219            return NO_ERROR;
1220        } break;
1221        case RELEASE_AUDIO_SESSION_ID: {
1222            CHECK_INTERFACE(IAudioFlinger, data, reply);
1223            int audioSession = data.readInt32();
1224            int pid = data.readInt32();
1225            releaseAudioSessionId(audioSession, pid);
1226            return NO_ERROR;
1227        } break;
1228        case QUERY_NUM_EFFECTS: {
1229            CHECK_INTERFACE(IAudioFlinger, data, reply);
1230            uint32_t numEffects;
1231            status_t status = queryNumberEffects(&numEffects);
1232            reply->writeInt32(status);
1233            if (status == NO_ERROR) {
1234                reply->writeInt32((int32_t)numEffects);
1235            }
1236            return NO_ERROR;
1237        }
1238        case QUERY_EFFECT: {
1239            CHECK_INTERFACE(IAudioFlinger, data, reply);
1240            effect_descriptor_t desc;
1241            status_t status = queryEffect(data.readInt32(), &desc);
1242            reply->writeInt32(status);
1243            if (status == NO_ERROR) {
1244                reply->write(&desc, sizeof(effect_descriptor_t));
1245            }
1246            return NO_ERROR;
1247        }
1248        case GET_EFFECT_DESCRIPTOR: {
1249            CHECK_INTERFACE(IAudioFlinger, data, reply);
1250            effect_uuid_t uuid;
1251            data.read(&uuid, sizeof(effect_uuid_t));
1252            effect_descriptor_t desc;
1253            status_t status = getEffectDescriptor(&uuid, &desc);
1254            reply->writeInt32(status);
1255            if (status == NO_ERROR) {
1256                reply->write(&desc, sizeof(effect_descriptor_t));
1257            }
1258            return NO_ERROR;
1259        }
1260        case CREATE_EFFECT: {
1261            CHECK_INTERFACE(IAudioFlinger, data, reply);
1262            effect_descriptor_t desc;
1263            data.read(&desc, sizeof(effect_descriptor_t));
1264            sp<IEffectClient> client = interface_cast<IEffectClient>(data.readStrongBinder());
1265            int32_t priority = data.readInt32();
1266            audio_io_handle_t output = (audio_io_handle_t) data.readInt32();
1267            int sessionId = data.readInt32();
1268            status_t status;
1269            int id;
1270            int enabled;
1271
1272            sp<IEffect> effect = createEffect(&desc, client, priority, output, sessionId,
1273                    &status, &id, &enabled);
1274            reply->writeInt32(status);
1275            reply->writeInt32(id);
1276            reply->writeInt32(enabled);
1277            reply->writeStrongBinder(effect->asBinder());
1278            reply->write(&desc, sizeof(effect_descriptor_t));
1279            return NO_ERROR;
1280        } break;
1281        case MOVE_EFFECTS: {
1282            CHECK_INTERFACE(IAudioFlinger, data, reply);
1283            int session = data.readInt32();
1284            audio_io_handle_t srcOutput = (audio_io_handle_t) data.readInt32();
1285            audio_io_handle_t dstOutput = (audio_io_handle_t) data.readInt32();
1286            reply->writeInt32(moveEffects(session, srcOutput, dstOutput));
1287            return NO_ERROR;
1288        } break;
1289        case LOAD_HW_MODULE: {
1290            CHECK_INTERFACE(IAudioFlinger, data, reply);
1291            reply->writeInt32(loadHwModule(data.readCString()));
1292            return NO_ERROR;
1293        } break;
1294        case GET_PRIMARY_OUTPUT_SAMPLING_RATE: {
1295            CHECK_INTERFACE(IAudioFlinger, data, reply);
1296            reply->writeInt32(getPrimaryOutputSamplingRate());
1297            return NO_ERROR;
1298        } break;
1299        case GET_PRIMARY_OUTPUT_FRAME_COUNT: {
1300            CHECK_INTERFACE(IAudioFlinger, data, reply);
1301            reply->writeInt64(getPrimaryOutputFrameCount());
1302            return NO_ERROR;
1303        } break;
1304        case SET_LOW_RAM_DEVICE: {
1305            CHECK_INTERFACE(IAudioFlinger, data, reply);
1306            bool isLowRamDevice = data.readInt32() != 0;
1307            reply->writeInt32(setLowRamDevice(isLowRamDevice));
1308            return NO_ERROR;
1309        } break;
1310        case LIST_AUDIO_PORTS: {
1311            CHECK_INTERFACE(IAudioFlinger, data, reply);
1312            unsigned int num_ports = data.readInt32();
1313            struct audio_port *ports =
1314                    (struct audio_port *)calloc(num_ports,
1315                                                           sizeof(struct audio_port));
1316            status_t status = listAudioPorts(&num_ports, ports);
1317            reply->writeInt32(status);
1318            if (status == NO_ERROR) {
1319                reply->writeInt32(num_ports);
1320                reply->write(&ports, num_ports * sizeof(struct audio_port));
1321            }
1322            free(ports);
1323            return NO_ERROR;
1324        } break;
1325        case GET_AUDIO_PORT: {
1326            CHECK_INTERFACE(IAudioFlinger, data, reply);
1327            struct audio_port port;
1328            data.read(&port, sizeof(struct audio_port));
1329            status_t status = getAudioPort(&port);
1330            reply->writeInt32(status);
1331            if (status == NO_ERROR) {
1332                reply->write(&port, sizeof(struct audio_port));
1333            }
1334            return NO_ERROR;
1335        } break;
1336        case CREATE_AUDIO_PATCH: {
1337            CHECK_INTERFACE(IAudioFlinger, data, reply);
1338            struct audio_patch patch;
1339            data.read(&patch, sizeof(struct audio_patch));
1340            audio_patch_handle_t handle;
1341            data.read(&handle, sizeof(audio_patch_handle_t));
1342            status_t status = createAudioPatch(&patch, &handle);
1343            reply->writeInt32(status);
1344            if (status == NO_ERROR) {
1345                reply->write(&handle, sizeof(audio_patch_handle_t));
1346            }
1347            return NO_ERROR;
1348        } break;
1349        case RELEASE_AUDIO_PATCH: {
1350            CHECK_INTERFACE(IAudioFlinger, data, reply);
1351            audio_patch_handle_t handle;
1352            data.read(&handle, sizeof(audio_patch_handle_t));
1353            status_t status = releaseAudioPatch(handle);
1354            reply->writeInt32(status);
1355            return NO_ERROR;
1356        } break;
1357        case LIST_AUDIO_PATCHES: {
1358            CHECK_INTERFACE(IAudioFlinger, data, reply);
1359            unsigned int num_patches = data.readInt32();
1360            struct audio_patch *patches =
1361                    (struct audio_patch *)calloc(num_patches,
1362                                                 sizeof(struct audio_patch));
1363            status_t status = listAudioPatches(&num_patches, patches);
1364            reply->writeInt32(status);
1365            if (status == NO_ERROR) {
1366                reply->writeInt32(num_patches);
1367                reply->write(&patches, num_patches * sizeof(struct audio_patch));
1368            }
1369            free(patches);
1370            return NO_ERROR;
1371        } break;
1372        case SET_AUDIO_PORT_CONFIG: {
1373            CHECK_INTERFACE(IAudioFlinger, data, reply);
1374            struct audio_port_config config;
1375            data.read(&config, sizeof(struct audio_port_config));
1376            status_t status = setAudioPortConfig(&config);
1377            reply->writeInt32(status);
1378            return NO_ERROR;
1379        } break;
1380        default:
1381            return BBinder::onTransact(code, data, reply, flags);
1382    }
1383}
1384
1385// ----------------------------------------------------------------------------
1386
1387}; // namespace android
1388