classes.c revision 527f8ca99f2938d6569fc25dcf3256985a54dec6
1/*
2 * Copyright (C) 2010 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17/* Classes vs. interfaces */
18
19#include "sles_allinclusive.h"
20
21
22#if USE_PROFILES & USE_PROFILES_GAME
23
24// 3DGroup class
25
26static const struct iid_vtable _3DGroup_interfaces[INTERFACES_3DGroup] = {
27    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(C3DGroup, mObject)},
28    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
29        offsetof(C3DGroup, mDynamicInterfaceManagement)},
30    {MPH_3DLOCATION, INTERFACE_IMPLICIT, offsetof(C3DGroup, m3DLocation)},
31    {MPH_3DDOPPLER, INTERFACE_DYNAMIC_GAME, offsetof(C3DGroup, m3DDoppler)},
32    {MPH_3DSOURCE, INTERFACE_EXPLICIT_GAME, offsetof(C3DGroup, m3DSource)},
33    {MPH_3DMACROSCOPIC, INTERFACE_OPTIONAL, offsetof(C3DGroup, m3DMacroscopic)},
34};
35
36static const ClassTable C3DGroup_class = {
37    _3DGroup_interfaces,
38    INTERFACES_3DGroup,
39    MPH_to_3DGroup,
40    "3DGroup",
41    sizeof(C3DGroup),
42    SL_OBJECTID_3DGROUP,
43    0,      // OpenMAX AL object ID
44    NULL,
45    NULL,
46    NULL,
47    C3DGroup_PreDestroy
48};
49
50#endif
51
52
53// AudioPlayer class
54
55static const struct iid_vtable AudioPlayer_interfaces[INTERFACES_AudioPlayer] = {
56    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CAudioPlayer, mObject)},
57    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
58        offsetof(CAudioPlayer, mDynamicInterfaceManagement)},
59    {MPH_PLAY, INTERFACE_IMPLICIT, offsetof(CAudioPlayer, mPlay)},
60    {MPH_3DDOPPLER, INTERFACE_DYNAMIC_GAME, offsetof(CAudioPlayer, m3DDoppler)},
61    {MPH_3DGROUPING, INTERFACE_EXPLICIT_GAME, offsetof(CAudioPlayer, m3DGrouping)},
62    {MPH_3DLOCATION, INTERFACE_EXPLICIT_GAME, offsetof(CAudioPlayer, m3DLocation)},
63    {MPH_3DSOURCE, INTERFACE_EXPLICIT_GAME, offsetof(CAudioPlayer, m3DSource)},
64    {MPH_BUFFERQUEUE, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mBufferQueue)},
65    {MPH_EFFECTSEND, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mEffectSend)},
66    {MPH_MUTESOLO, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mMuteSolo)},
67    {MPH_METADATAEXTRACTION, INTERFACE_DYNAMIC_GAME_MUSIC,
68        offsetof(CAudioPlayer, mMetadataExtraction)},
69    {MPH_METADATATRAVERSAL, INTERFACE_DYNAMIC_GAME_MUSIC,
70        offsetof(CAudioPlayer, mMetadataTraversal)},
71    {MPH_PREFETCHSTATUS, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mPrefetchStatus)},
72    {MPH_RATEPITCH, INTERFACE_DYNAMIC_GAME, offsetof(CAudioPlayer, mRatePitch)},
73    {MPH_SEEK, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mSeek)},
74    // The base Volume interface is explicit, but portions are only for Game and Music profiles
75    {MPH_VOLUME, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mVolume)},
76    {MPH_3DMACROSCOPIC, INTERFACE_OPTIONAL, offsetof(CAudioPlayer, m3DMacroscopic)},
77    {MPH_BASSBOOST, INTERFACE_DYNAMIC, offsetof(CAudioPlayer, mBassBoost)},
78    {MPH_DYNAMICSOURCE, INTERFACE_OPTIONAL, offsetof(CAudioPlayer, mDynamicSource)},
79    {MPH_ENVIRONMENTALREVERB, INTERFACE_DYNAMIC,
80        offsetof(CAudioPlayer, mEnvironmentalReverb)},
81    {MPH_EQUALIZER, INTERFACE_DYNAMIC, offsetof(CAudioPlayer, mEqualizer)},
82    {MPH_PITCH, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CAudioPlayer, mPitch)},
83    {MPH_PRESETREVERB, INTERFACE_DYNAMIC, offsetof(CAudioPlayer, mPresetReverb)},
84    {MPH_PLAYBACKRATE, INTERFACE_DYNAMIC, offsetof(CAudioPlayer, mPlaybackRate)},
85    {MPH_VIRTUALIZER, INTERFACE_DYNAMIC, offsetof(CAudioPlayer, mVirtualizer)},
86    {MPH_VISUALIZATION, INTERFACE_OPTIONAL, offsetof(CAudioPlayer, mVisualization)},
87#ifdef ANDROID
88    {MPH_ANDROIDEFFECT, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mAndroidEffect)},
89    {MPH_ANDROIDEFFECTSEND, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mAndroidEffectSend)},
90    {MPH_ANDROIDCONFIGURATION, INTERFACE_EXPLICIT_PREREALIZE,
91            offsetof(CAudioPlayer, mAndroidConfiguration)},
92    {MPH_ANDROIDBUFFERQUEUE, INTERFACE_EXPLICIT, offsetof(CAudioPlayer, mAndroidBufferQueue)},
93#endif
94};
95
96static const ClassTable CAudioPlayer_class = {
97    AudioPlayer_interfaces,
98    INTERFACES_AudioPlayer,
99    MPH_to_AudioPlayer,
100    "AudioPlayer",
101    sizeof(CAudioPlayer),
102    SL_OBJECTID_AUDIOPLAYER,
103    0,      // OpenMAX AL object ID
104    CAudioPlayer_Realize,
105    CAudioPlayer_Resume,
106    CAudioPlayer_Destroy,
107    CAudioPlayer_PreDestroy
108};
109
110
111#if (USE_PROFILES & USE_PROFILES_OPTIONAL) || defined(ANDROID)
112
113// AudioRecorder class
114
115static const struct iid_vtable AudioRecorder_interfaces[INTERFACES_AudioRecorder] = {
116    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CAudioRecorder, mObject)},
117    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
118        offsetof(CAudioRecorder, mDynamicInterfaceManagement)},
119    {MPH_RECORD, INTERFACE_IMPLICIT, offsetof(CAudioRecorder, mRecord)},
120    {MPH_AUDIOENCODER, INTERFACE_EXPLICIT, offsetof(CAudioRecorder, mAudioEncoder)},
121    {MPH_BASSBOOST, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CAudioRecorder, mBassBoost)},
122    {MPH_DYNAMICSOURCE, INTERFACE_OPTIONAL, offsetof(CAudioRecorder, mDynamicSource)},
123    {MPH_EQUALIZER, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CAudioRecorder, mEqualizer)},
124    {MPH_VISUALIZATION, INTERFACE_OPTIONAL, offsetof(CAudioRecorder, mVisualization)},
125    {MPH_VOLUME, INTERFACE_OPTIONAL, offsetof(CAudioRecorder, mVolume)},
126#ifdef ANDROID
127    {MPH_ANDROIDSIMPLEBUFFERQUEUE, INTERFACE_EXPLICIT, offsetof(CAudioRecorder, mBufferQueue)},
128    {MPH_ANDROIDCONFIGURATION, INTERFACE_EXPLICIT_PREREALIZE,
129            offsetof(CAudioRecorder, mAndroidConfiguration)},
130#endif
131};
132
133static const ClassTable CAudioRecorder_class = {
134    AudioRecorder_interfaces,
135    INTERFACES_AudioRecorder,
136    MPH_to_AudioRecorder,
137    "AudioRecorder",
138    sizeof(CAudioRecorder),
139    SL_OBJECTID_AUDIORECORDER,
140    0,      // OpenMAX AL object ID
141    CAudioRecorder_Realize,
142    CAudioRecorder_Resume,
143    CAudioRecorder_Destroy,
144    CAudioRecorder_PreDestroy
145};
146
147#endif
148
149
150// Engine class
151
152static const struct iid_vtable Engine_interfaces[INTERFACES_Engine] = {
153    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CEngine, mObject)},
154    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
155        offsetof(CEngine, mDynamicInterfaceManagement)},
156    {MPH_ENGINE, INTERFACE_IMPLICIT, offsetof(CEngine, mEngine)},
157    {MPH_ENGINECAPABILITIES, INTERFACE_IMPLICIT_BASE, offsetof(CEngine, mEngineCapabilities)},
158    {MPH_THREADSYNC, INTERFACE_IMPLICIT_BASE, offsetof(CEngine, mThreadSync)},
159    {MPH_AUDIOIODEVICECAPABILITIES, INTERFACE_IMPLICIT_BASE,
160        offsetof(CEngine, mAudioIODeviceCapabilities)},
161    {MPH_AUDIODECODERCAPABILITIES, INTERFACE_EXPLICIT_BASE,
162        offsetof(CEngine, mAudioDecoderCapabilities)},
163    {MPH_AUDIOENCODERCAPABILITIES, INTERFACE_EXPLICIT_BASE,
164        offsetof(CEngine, mAudioEncoderCapabilities)},
165    {MPH_3DCOMMIT, INTERFACE_EXPLICIT_GAME, offsetof(CEngine, m3DCommit)},
166    {MPH_DEVICEVOLUME, INTERFACE_OPTIONAL, offsetof(CEngine, mDeviceVolume)},
167    {MPH_XAENGINE, INTERFACE_IMPLICIT, offsetof(CEngine, mXAEngine)},
168#ifdef ANDROID
169    {MPH_ANDROIDEFFECTCAPABILITIES, INTERFACE_EXPLICIT,
170        offsetof(CEngine, mAndroidEffectCapabilities)},
171#endif
172};
173
174static const ClassTable CEngine_class = {
175    Engine_interfaces,
176    INTERFACES_Engine,
177    MPH_to_Engine,
178    "Engine",
179    sizeof(CEngine),
180    SL_OBJECTID_ENGINE,
181    XA_OBJECTID_ENGINE,
182    CEngine_Realize,
183    CEngine_Resume,
184    CEngine_Destroy,
185    CEngine_PreDestroy
186};
187
188
189#if USE_PROFILES & USE_PROFILES_OPTIONAL
190
191// LEDDevice class
192
193static const struct iid_vtable LEDDevice_interfaces[INTERFACES_LEDDevice] = {
194    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CLEDDevice, mObject)},
195    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
196        offsetof(CLEDDevice, mDynamicInterfaceManagement)},
197    {MPH_LED, INTERFACE_IMPLICIT, offsetof(CLEDDevice, mLEDArray)},
198};
199
200static const ClassTable CLEDDevice_class = {
201    LEDDevice_interfaces,
202    INTERFACES_LEDDevice,
203    MPH_to_LEDDevice,
204    "LEDDevice",
205    sizeof(CLEDDevice),
206    SL_OBJECTID_LEDDEVICE,
207    XA_OBJECTID_LEDDEVICE,
208    NULL,
209    NULL,
210    NULL,
211    NULL
212};
213
214#endif
215
216
217#if USE_PROFILES & USE_PROFILES_GAME
218
219// Listener class
220
221static const struct iid_vtable Listener_interfaces[INTERFACES_Listener] = {
222    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CListener, mObject)},
223    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
224        offsetof(CListener, mDynamicInterfaceManagement)},
225    {MPH_3DDOPPLER, INTERFACE_DYNAMIC_GAME, offsetof(CListener, m3DDoppler)},
226    {MPH_3DLOCATION, INTERFACE_EXPLICIT_GAME, offsetof(CListener, m3DLocation)},
227};
228
229static const ClassTable CListener_class = {
230    Listener_interfaces,
231    INTERFACES_Listener,
232    MPH_to_Listener,
233    "Listener",
234    sizeof(CListener),
235    SL_OBJECTID_LISTENER,
236    0,      // OpenMAX AL object ID
237    NULL,
238    NULL,
239    NULL,
240    NULL
241};
242
243#endif
244
245
246#if USE_PROFILES & (USE_PROFILES_GAME | USE_PROFILES_MUSIC)
247
248// MetadataExtractor class
249
250static const struct iid_vtable MetadataExtractor_interfaces[INTERFACES_MetadataExtractor] = {
251    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CMetadataExtractor, mObject)},
252    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
253        offsetof(CMetadataExtractor, mDynamicInterfaceManagement)},
254    {MPH_DYNAMICSOURCE, INTERFACE_IMPLICIT, offsetof(CMetadataExtractor, mDynamicSource)},
255    {MPH_METADATAEXTRACTION, INTERFACE_IMPLICIT, offsetof(CMetadataExtractor, mMetadataExtraction)},
256    {MPH_METADATATRAVERSAL, INTERFACE_IMPLICIT, offsetof(CMetadataExtractor, mMetadataTraversal)},
257};
258
259static const ClassTable CMetadataExtractor_class = {
260    MetadataExtractor_interfaces,
261    INTERFACES_MetadataExtractor,
262    MPH_to_MetadataExtractor,
263    "MetadataExtractor",
264    sizeof(CMetadataExtractor),
265    SL_OBJECTID_METADATAEXTRACTOR,
266    XA_OBJECTID_METADATAEXTRACTOR,
267    NULL,
268    NULL,
269    NULL,
270    NULL
271};
272
273#endif
274
275
276#if USE_PROFILES & USE_PROFILES_GAME
277
278// MidiPlayer class
279
280static const struct iid_vtable MidiPlayer_interfaces[INTERFACES_MidiPlayer] = {
281    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CMidiPlayer, mObject)},
282    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
283        offsetof(CMidiPlayer, mDynamicInterfaceManagement)},
284    {MPH_PLAY, INTERFACE_IMPLICIT, offsetof(CMidiPlayer, mPlay)},
285    {MPH_3DDOPPLER, INTERFACE_DYNAMIC_GAME, offsetof(C3DGroup, m3DDoppler)},
286    {MPH_3DGROUPING, INTERFACE_EXPLICIT_GAME, offsetof(CMidiPlayer, m3DGrouping)},
287    {MPH_3DLOCATION, INTERFACE_EXPLICIT_GAME, offsetof(CMidiPlayer, m3DLocation)},
288    {MPH_3DSOURCE, INTERFACE_EXPLICIT_GAME, offsetof(CMidiPlayer, m3DSource)},
289    {MPH_BUFFERQUEUE, INTERFACE_EXPLICIT_GAME, offsetof(CMidiPlayer, mBufferQueue)},
290    {MPH_EFFECTSEND, INTERFACE_EXPLICIT_GAME, offsetof(CMidiPlayer, mEffectSend)},
291    {MPH_MUTESOLO, INTERFACE_EXPLICIT_GAME, offsetof(CMidiPlayer, mMuteSolo)},
292    {MPH_METADATAEXTRACTION, INTERFACE_DYNAMIC_GAME, offsetof(CMidiPlayer, mMetadataExtraction)},
293    {MPH_METADATATRAVERSAL, INTERFACE_DYNAMIC_GAME, offsetof(CMidiPlayer, mMetadataTraversal)},
294    {MPH_MIDIMESSAGE, INTERFACE_EXPLICIT_GAME_PHONE, offsetof(CMidiPlayer, mMIDIMessage)},
295    {MPH_MIDITIME, INTERFACE_EXPLICIT_GAME_PHONE, offsetof(CMidiPlayer, mMIDITime)},
296    {MPH_MIDITEMPO, INTERFACE_EXPLICIT_GAME_PHONE, offsetof(CMidiPlayer, mMIDITempo)},
297    {MPH_MIDIMUTESOLO, INTERFACE_EXPLICIT_GAME, offsetof(CMidiPlayer, mMIDIMuteSolo)},
298    {MPH_PREFETCHSTATUS, INTERFACE_EXPLICIT_GAME_PHONE, offsetof(CMidiPlayer, mPrefetchStatus)},
299    {MPH_SEEK, INTERFACE_EXPLICIT_GAME_PHONE, offsetof(CMidiPlayer, mSeek)},
300    {MPH_VOLUME, INTERFACE_EXPLICIT_GAME_PHONE, offsetof(CMidiPlayer, mVolume)},
301    {MPH_3DMACROSCOPIC, INTERFACE_OPTIONAL, offsetof(CMidiPlayer, m3DMacroscopic)},
302    {MPH_BASSBOOST, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CMidiPlayer, mBassBoost)},
303    {MPH_DYNAMICSOURCE, INTERFACE_OPTIONAL, offsetof(CMidiPlayer, mDynamicSource)},
304    {MPH_ENVIRONMENTALREVERB, INTERFACE_DYNAMIC_OPTIONAL,
305        offsetof(CMidiPlayer, mEnvironmentalReverb)},
306    {MPH_EQUALIZER, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CMidiPlayer, mEqualizer)},
307    {MPH_PITCH, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CMidiPlayer, mPitch)},
308    {MPH_PRESETREVERB, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CMidiPlayer, mPresetReverb)},
309    {MPH_PLAYBACKRATE, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CMidiPlayer, mPlaybackRate)},
310    {MPH_VIRTUALIZER, INTERFACE_DYNAMIC_OPTIONAL, offsetof(CMidiPlayer, mVirtualizer)},
311    {MPH_VISUALIZATION, INTERFACE_OPTIONAL, offsetof(CMidiPlayer, mVisualization)},
312};
313
314static const ClassTable CMidiPlayer_class = {
315    MidiPlayer_interfaces,
316    INTERFACES_MidiPlayer,
317    MPH_to_MidiPlayer,
318    "MidiPlayer",
319    sizeof(CMidiPlayer),
320    SL_OBJECTID_MIDIPLAYER,
321    0,      // OpenMAX AL object ID
322    NULL,
323    NULL,
324    NULL,
325    NULL
326};
327
328#endif
329
330
331// OutputMix class
332
333static const struct iid_vtable OutputMix_interfaces[INTERFACES_OutputMix] = {
334    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(COutputMix, mObject)},
335    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
336        offsetof(COutputMix, mDynamicInterfaceManagement)},
337    {MPH_OUTPUTMIX, INTERFACE_IMPLICIT, offsetof(COutputMix, mOutputMix)},
338#ifdef USE_OUTPUTMIXEXT
339    {MPH_OUTPUTMIXEXT, INTERFACE_UNAVAILABLE, offsetof(COutputMix, mOutputMixExt)},
340#else
341    {MPH_OUTPUTMIXEXT, INTERFACE_UNAVAILABLE, 0},
342#endif
343    {MPH_ENVIRONMENTALREVERB, INTERFACE_DYNAMIC,
344        offsetof(COutputMix, mEnvironmentalReverb)},
345    {MPH_EQUALIZER, INTERFACE_DYNAMIC, offsetof(COutputMix, mEqualizer)},
346    {MPH_PRESETREVERB, INTERFACE_DYNAMIC, offsetof(COutputMix, mPresetReverb)},
347    {MPH_VIRTUALIZER, INTERFACE_DYNAMIC, offsetof(COutputMix, mVirtualizer)},
348    // The overall Volume interface is explicit optional,
349    // but portions of Volume are mandated only in Game and Music profiles
350    {MPH_VOLUME, INTERFACE_OPTIONAL, offsetof(COutputMix, mVolume)},
351    {MPH_BASSBOOST, INTERFACE_DYNAMIC, offsetof(COutputMix, mBassBoost)},
352    {MPH_VISUALIZATION, INTERFACE_OPTIONAL, offsetof(COutputMix, mVisualization)},
353#ifdef ANDROID
354    {MPH_ANDROIDEFFECT, INTERFACE_EXPLICIT, offsetof(COutputMix, mAndroidEffect)},
355#endif
356};
357
358static const ClassTable COutputMix_class = {
359    OutputMix_interfaces,
360    INTERFACES_OutputMix,
361    MPH_to_OutputMix,
362    "OutputMix",
363    sizeof(COutputMix),
364    SL_OBJECTID_OUTPUTMIX,
365    XA_OBJECTID_OUTPUTMIX,
366    COutputMix_Realize,
367    COutputMix_Resume,
368    COutputMix_Destroy,
369    COutputMix_PreDestroy
370};
371
372
373#if USE_PROFILES & USE_PROFILES_OPTIONAL
374
375// Vibra class
376
377static const struct iid_vtable VibraDevice_interfaces[INTERFACES_VibraDevice] = {
378    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CVibraDevice, mObject)},
379    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
380        offsetof(CVibraDevice, mDynamicInterfaceManagement)},
381    {MPH_VIBRA, INTERFACE_IMPLICIT, offsetof(CVibraDevice, mVibra)},
382};
383
384static const ClassTable CVibraDevice_class = {
385    VibraDevice_interfaces,
386    INTERFACES_VibraDevice,
387    MPH_to_Vibra,
388    "VibraDevice",
389    sizeof(CVibraDevice),
390    SL_OBJECTID_VIBRADEVICE,
391    XA_OBJECTID_VIBRADEVICE,
392    NULL,
393    NULL,
394    NULL,
395    NULL
396};
397
398#endif
399
400
401// Media player class
402
403static const struct iid_vtable MediaPlayer_interfaces[INTERFACES_MediaPlayer] = {
404    {MPH_OBJECT, INTERFACE_IMPLICIT_PREREALIZE, offsetof(CMediaPlayer, mObject)},
405    {MPH_DYNAMICINTERFACEMANAGEMENT, INTERFACE_IMPLICIT,
406        offsetof(CMediaPlayer, mDynamicInterfaceManagement)},
407    {MPH_XAPLAY, INTERFACE_IMPLICIT, offsetof(CMediaPlayer, mPlay)},
408    {MPH_XASTREAMINFORMATION, INTERFACE_EXPLICIT, offsetof(CMediaPlayer, mStreamInfo)},
409    {MPH_XAVOLUME, INTERFACE_IMPLICIT, offsetof(CMediaPlayer, mVolume)},
410#ifdef ANDROID
411    {MPH_ANDROIDBUFFERQUEUE, INTERFACE_EXPLICIT, offsetof(CMediaPlayer, mAndroidBufferQueue)},
412#endif
413};
414
415static const ClassTable CMediaPlayer_class = {
416    MediaPlayer_interfaces,
417    INTERFACES_MediaPlayer,
418    MPH_to_MediaPlayer,
419    "MediaPlayer",
420    sizeof(CMediaPlayer),
421    0,      // OpenSL ES object ID
422    XA_OBJECTID_MEDIAPLAYER,
423    CMediaPlayer_Realize,
424    CMediaPlayer_Resume,
425    CMediaPlayer_Destroy,
426    CMediaPlayer_PreDestroy
427};
428
429
430static const ClassTable * const slClasses[] = {
431    // Do not change order of these entries; they are in numerical order
432    &CEngine_class,
433#if USE_PROFILES & USE_PROFILES_OPTIONAL
434    &CLEDDevice_class,
435    &CVibraDevice_class,
436#else
437    NULL,
438    NULL,
439#endif
440    &CAudioPlayer_class,
441#if (USE_PROFILES & USE_PROFILES_OPTIONAL) || defined(ANDROID)
442    &CAudioRecorder_class,
443#else
444    NULL,
445#endif
446#if USE_PROFILES & (USE_PROFILES_GAME | USE_PROFILES_PHONE)
447    &CMidiPlayer_class,
448#else
449    NULL,
450#endif
451#if USE_PROFILES & USE_PROFILES_GAME
452    &CListener_class,
453    &C3DGroup_class,
454#else
455    NULL,
456    NULL,
457#endif
458    &COutputMix_class,
459#if USE_PROFILES & (USE_PROFILES_GAME | USE_PROFILES_MUSIC)
460    &CMetadataExtractor_class
461#else
462    NULL
463#endif
464};
465
466
467static const ClassTable * const xaClasses[] = {
468    &CEngine_class,
469#if USE_PROFILES & USE_PROFILES_OPTIONAL
470    &CLEDDevice_class,
471    &CVibraDevice_class,
472#else
473    NULL,
474    NULL,
475#endif
476    &CMediaPlayer_class,
477#if 1
478    NULL,
479    NULL,
480#else
481    &CMediaRecorder_class,
482    &CRadioDevice_class,
483#endif
484    &COutputMix_class,
485#if USE_PROFILES & (USE_PROFILES_GAME | USE_PROFILES_MUSIC)
486    &CMetadataExtractor_class,
487#else
488    NULL,
489#endif
490#if 1
491    NULL
492#else
493    &CCameraDevice_class
494#endif
495};
496
497
498/* \brief Map SL_OBJECTID to class or NULL if object ID not supported */
499
500LI_API const ClassTable *objectIDtoClass(SLuint32 objectID)
501{
502    // object ID is the engine and always present
503    assert(NULL != slClasses[0]);
504    SLuint32 slObjectID0 = slClasses[0]->mSLObjectID;
505    if ((slObjectID0 <= objectID) && ((slObjectID0 + sizeof(slClasses)/sizeof(slClasses[0])) >
506            objectID)) {
507        return slClasses[objectID - slObjectID0];
508    }
509    assert(NULL != xaClasses[0]);
510    SLuint32 xaObjectID0 = xaClasses[0]->mXAObjectID;
511    if ((xaObjectID0 <= objectID) && ((xaObjectID0 + sizeof(xaClasses)/sizeof(xaClasses[0])) >
512            objectID)) {
513        return xaClasses[objectID - xaObjectID0];
514    }
515    return NULL;
516}
517