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/* MIDIMuteSolo implementation */
18
19#include "sles_allinclusive.h"
20
21
22static SLresult IMIDIMuteSolo_SetChannelMute(SLMIDIMuteSoloItf self, SLuint8 channel,
23    SLboolean mute)
24{
25    SL_ENTER_INTERFACE
26
27    if (channel > 15) {
28        result = SL_RESULT_PARAMETER_INVALID;
29    } else {
30        IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
31        SLuint16 mask = 1 << channel;
32        interface_lock_exclusive(thiz);
33        if (mute)
34            thiz->mChannelMuteMask |= mask;
35        else
36            thiz->mChannelMuteMask &= ~mask;
37        interface_unlock_exclusive(thiz);
38        result = SL_RESULT_SUCCESS;
39    }
40
41    SL_LEAVE_INTERFACE
42}
43
44
45static SLresult IMIDIMuteSolo_GetChannelMute(SLMIDIMuteSoloItf self, SLuint8 channel,
46    SLboolean *pMute)
47{
48    SL_ENTER_INTERFACE
49
50    if (channel > 15 || (NULL == pMute)) {
51        result = SL_RESULT_PARAMETER_INVALID;
52    } else {
53        IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
54        interface_lock_peek(thiz);
55        SLuint16 mask = thiz->mChannelMuteMask;
56        interface_unlock_peek(thiz);
57        *pMute = (mask >> channel) & 1;
58        result = SL_RESULT_SUCCESS;
59    }
60
61    SL_LEAVE_INTERFACE
62}
63
64
65static SLresult IMIDIMuteSolo_SetChannelSolo(SLMIDIMuteSoloItf self, SLuint8 channel,
66    SLboolean solo)
67{
68    SL_ENTER_INTERFACE
69
70    if (channel > 15) {
71        result = SL_RESULT_PARAMETER_INVALID;
72    } else {
73        IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
74        SLuint16 mask = 1 << channel;
75        interface_lock_exclusive(thiz);
76        if (solo)
77            thiz->mChannelSoloMask |= mask;
78        else
79            thiz->mChannelSoloMask &= ~mask;
80        interface_unlock_exclusive(thiz);
81        result = SL_RESULT_SUCCESS;
82    }
83
84    SL_LEAVE_INTERFACE
85}
86
87
88static SLresult IMIDIMuteSolo_GetChannelSolo(SLMIDIMuteSoloItf self, SLuint8 channel,
89    SLboolean *pSolo)
90{
91    SL_ENTER_INTERFACE
92
93    if (channel > 15 || (NULL == pSolo)) {
94        result = SL_RESULT_PARAMETER_INVALID;
95    } else {
96        IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
97        interface_lock_peek(thiz);
98        SLuint16 mask = thiz->mChannelSoloMask;
99        interface_unlock_peek(thiz);
100        *pSolo = (mask >> channel) & 1;
101        result = SL_RESULT_SUCCESS;
102    }
103
104    SL_LEAVE_INTERFACE
105}
106
107
108static SLresult IMIDIMuteSolo_GetTrackCount(SLMIDIMuteSoloItf self, SLuint16 *pCount)
109{
110    SL_ENTER_INTERFACE
111
112    if (NULL == pCount) {
113        result = SL_RESULT_PARAMETER_INVALID;
114    } else {
115        IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
116        // const, so no lock needed
117        SLuint16 trackCount = thiz->mTrackCount;
118        *pCount = trackCount;
119        result = SL_RESULT_SUCCESS;
120    }
121
122    SL_LEAVE_INTERFACE
123}
124
125
126static SLresult IMIDIMuteSolo_SetTrackMute(SLMIDIMuteSoloItf self, SLuint16 track, SLboolean mute)
127{
128    SL_ENTER_INTERFACE
129
130    IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
131    // const
132    if (!(track < thiz->mTrackCount)) {
133        result = SL_RESULT_PARAMETER_INVALID;
134    } else {
135        SLuint32 mask = 1 << track;
136        interface_lock_exclusive(thiz);
137        if (mute)
138            thiz->mTrackMuteMask |= mask;
139        else
140            thiz->mTrackMuteMask &= ~mask;
141        interface_unlock_exclusive(thiz);
142        result = SL_RESULT_SUCCESS;
143    }
144
145    SL_LEAVE_INTERFACE
146}
147
148
149static SLresult IMIDIMuteSolo_GetTrackMute(SLMIDIMuteSoloItf self, SLuint16 track, SLboolean *pMute)
150{
151    SL_ENTER_INTERFACE
152
153    IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
154    // const, no lock needed
155    if (!(track < thiz->mTrackCount) || NULL == pMute) {
156        result = SL_RESULT_PARAMETER_INVALID;
157    } else {
158        interface_lock_peek(thiz);
159        SLuint32 mask = thiz->mTrackMuteMask;
160        interface_unlock_peek(thiz);
161        *pMute = (mask >> track) & 1;
162        result = SL_RESULT_SUCCESS;
163    }
164
165    SL_LEAVE_INTERFACE
166}
167
168
169static SLresult IMIDIMuteSolo_SetTrackSolo(SLMIDIMuteSoloItf self, SLuint16 track, SLboolean solo)
170{
171    SL_ENTER_INTERFACE
172
173    IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
174    // const
175    if (!(track < thiz->mTrackCount)) {
176        result = SL_RESULT_PARAMETER_INVALID;
177    } else {
178        SLuint32 mask = 1 << track; interface_lock_exclusive(thiz);
179        if (solo)
180            thiz->mTrackSoloMask |= mask;
181        else
182            thiz->mTrackSoloMask &= ~mask;
183        interface_unlock_exclusive(thiz);
184        result = SL_RESULT_SUCCESS;
185    }
186
187    SL_LEAVE_INTERFACE
188}
189
190
191static SLresult IMIDIMuteSolo_GetTrackSolo(SLMIDIMuteSoloItf self, SLuint16 track, SLboolean *pSolo)
192{
193    SL_ENTER_INTERFACE
194
195    IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
196    // const, no lock needed
197    if (!(track < thiz->mTrackCount) || NULL == pSolo) {
198        result = SL_RESULT_PARAMETER_INVALID;
199    } else {
200        interface_lock_peek(thiz);
201        SLuint32 mask = thiz->mTrackSoloMask;
202        interface_unlock_peek(thiz);
203        *pSolo = (mask >> track) & 1;
204        result = SL_RESULT_SUCCESS;
205    }
206
207    SL_LEAVE_INTERFACE
208}
209
210
211static const struct SLMIDIMuteSoloItf_ IMIDIMuteSolo_Itf = {
212    IMIDIMuteSolo_SetChannelMute,
213    IMIDIMuteSolo_GetChannelMute,
214    IMIDIMuteSolo_SetChannelSolo,
215    IMIDIMuteSolo_GetChannelSolo,
216    IMIDIMuteSolo_GetTrackCount,
217    IMIDIMuteSolo_SetTrackMute,
218    IMIDIMuteSolo_GetTrackMute,
219    IMIDIMuteSolo_SetTrackSolo,
220    IMIDIMuteSolo_GetTrackSolo
221};
222
223void IMIDIMuteSolo_init(void *self)
224{
225    IMIDIMuteSolo *thiz = (IMIDIMuteSolo *) self;
226    thiz->mItf = &IMIDIMuteSolo_Itf;
227    thiz->mChannelMuteMask = 0;
228    thiz->mChannelSoloMask = 0;
229    thiz->mTrackMuteMask = 0;
230    thiz->mTrackSoloMask = 0;
231    // const
232    thiz->mTrackCount = 32; // wrong
233}
234