• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2017 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 #ifndef AAUDIO_EXAMPLE_ARGS_PARSER_H
18 #define AAUDIO_EXAMPLE_ARGS_PARSER_H
19 
20 #include <cctype>
21 #include <unistd.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 
25 #include <aaudio/AAudio.h>
26 #include <aaudio/AAudioTesting.h>
27 
28 #include "AAudioExampleUtils.h"
29 
30 // TODO use this as a base class within AAudio
31 class AAudioParameters {
32 public:
33 
34     /**
35      * This is also known as samplesPerFrame.
36      */
getChannelCount()37     int32_t getChannelCount() const {
38         return mChannelCount;
39     }
40 
setChannelCount(int32_t channelCount)41     void setChannelCount(int32_t channelCount) {
42         mChannelCount = channelCount;
43     }
44 
getSampleRate()45     int32_t getSampleRate() const {
46         return mSampleRate;
47     }
48 
setSampleRate(int32_t sampleRate)49     void setSampleRate(int32_t sampleRate) {
50         mSampleRate = sampleRate;
51     }
52 
getFormat()53     aaudio_format_t getFormat() const {
54         return mFormat;
55     }
56 
setFormat(aaudio_format_t format)57     void setFormat(aaudio_format_t format) {
58         mFormat = format;
59     }
60 
getSharingMode()61     aaudio_sharing_mode_t getSharingMode() const {
62         return mSharingMode;
63     }
64 
setSharingMode(aaudio_sharing_mode_t sharingMode)65     void setSharingMode(aaudio_sharing_mode_t sharingMode) {
66         mSharingMode = sharingMode;
67     }
68 
getBufferCapacity()69     int32_t getBufferCapacity() const {
70         return mBufferCapacity;
71     }
72 
setBufferCapacity(int32_t frames)73     void setBufferCapacity(int32_t frames) {
74         mBufferCapacity = frames;
75     }
76 
getPerformanceMode()77     int32_t getPerformanceMode() const {
78         return mPerformanceMode;
79     }
80 
setPerformanceMode(aaudio_performance_mode_t performanceMode)81     void setPerformanceMode(aaudio_performance_mode_t performanceMode) {
82         mPerformanceMode = performanceMode;
83     }
84 
getDeviceId()85     int32_t getDeviceId() const {
86         return mDeviceId;
87     }
88 
setDeviceId(int32_t deviceId)89     void setDeviceId(int32_t deviceId) {
90         mDeviceId = deviceId;
91     }
92 
getNumberOfBursts()93     int32_t getNumberOfBursts() const {
94         return mNumberOfBursts;
95     }
96 
setNumberOfBursts(int32_t numBursts)97     void setNumberOfBursts(int32_t numBursts) {
98         mNumberOfBursts = numBursts;
99     }
100 
101     /**
102      * Apply these parameters to a stream builder.
103      * @param builder
104      */
applyParameters(AAudioStreamBuilder * builder)105     void applyParameters(AAudioStreamBuilder *builder) const {
106         AAudioStreamBuilder_setChannelCount(builder, mChannelCount);
107         AAudioStreamBuilder_setFormat(builder, mFormat);
108         AAudioStreamBuilder_setSampleRate(builder, mSampleRate);
109         AAudioStreamBuilder_setBufferCapacityInFrames(builder, mBufferCapacity);
110         AAudioStreamBuilder_setDeviceId(builder, mDeviceId);
111         AAudioStreamBuilder_setSharingMode(builder, mSharingMode);
112         AAudioStreamBuilder_setPerformanceMode(builder, mPerformanceMode);
113     }
114 
115 private:
116     int32_t                    mChannelCount    = AAUDIO_UNSPECIFIED;
117     aaudio_format_t            mFormat          = AAUDIO_FORMAT_UNSPECIFIED;
118     int32_t                    mSampleRate      = AAUDIO_UNSPECIFIED;
119 
120     int32_t                    mBufferCapacity  = AAUDIO_UNSPECIFIED;
121     int32_t                    mDeviceId        = AAUDIO_UNSPECIFIED;
122     aaudio_sharing_mode_t      mSharingMode     = AAUDIO_SHARING_MODE_SHARED;
123     aaudio_performance_mode_t  mPerformanceMode = AAUDIO_PERFORMANCE_MODE_NONE;
124 
125     int32_t                    mNumberOfBursts  = AAUDIO_UNSPECIFIED;
126 };
127 
128 class AAudioArgsParser : public AAudioParameters {
129 public:
130     AAudioArgsParser() = default;
131     ~AAudioArgsParser() = default;
132 
133     enum {
134         DEFAULT_DURATION_SECONDS = 5
135     };
136 
137     /**
138      * @param arg
139      * @return true if the argument was not handled
140      */
parseArg(const char * arg)141     bool parseArg(const char *arg) {
142         bool unrecognized = false;
143         if (arg[0] == '-') {
144             char option = arg[1];
145             switch (option) {
146                 case 'b':
147                     setBufferCapacity(atoi(&arg[2]));
148                     break;
149                 case 'c':
150                     setChannelCount(atoi(&arg[2]));
151                     break;
152                 case 'd':
153                     setDeviceId(atoi(&arg[2]));
154                     break;
155                 case 's':
156                     mDurationSeconds = atoi(&arg[2]);
157                     break;
158                 case 'm': {
159                     aaudio_policy_t policy = AAUDIO_POLICY_AUTO;
160                     if (strlen(arg) > 2) {
161                         policy = atoi(&arg[2]);
162                     }
163                     AAudio_setMMapPolicy(policy);
164                 } break;
165                 case 'n':
166                     setNumberOfBursts(atoi(&arg[2]));
167                     break;
168                 case 'p':
169                     setPerformanceMode(parsePerformanceMode(arg[2]));
170                     break;
171                 case 'r':
172                     setSampleRate(atoi(&arg[2]));
173                     break;
174                 case 'x':
175                     setSharingMode(AAUDIO_SHARING_MODE_EXCLUSIVE);
176                     break;
177                 default:
178                     unrecognized = true;
179                     break;
180             }
181         }
182         return unrecognized;
183     }
184 
185     /**
186      *
187      * @param argc
188      * @param argv
189      * @return true if an unrecognized argument was passed
190      */
parseArgs(int argc,const char ** argv)191     bool parseArgs(int argc, const char **argv) {
192         for (int i = 1; i < argc; i++) {
193             const char *arg = argv[i];
194             if (parseArg(arg)) {
195                 usage();
196                 return true;
197             }
198 
199         }
200         return false;
201     }
202 
usage()203     static void usage() {
204         printf("-c{channels} -d{duration} -m -n{burstsPerBuffer} -p{perfMode} -r{rate} -x\n");
205         printf("      Default values are UNSPECIFIED unless otherwise stated.\n");
206         printf("      -b{bufferCapacity} frames\n");
207         printf("      -c{channels} for example 2 for stereo\n");
208         printf("      -d{deviceId} default is %d\n", AAUDIO_UNSPECIFIED);
209         printf("      -s{duration} in seconds, default is %d\n", DEFAULT_DURATION_SECONDS);
210         printf("      -m{0|1|2|3} set MMAP policy\n");
211         printf("          0 = _UNSPECIFIED, default\n");
212         printf("          1 = _NEVER\n");
213         printf("          2 = _AUTO, also if -m is used with no number\n");
214         printf("          3 = _ALWAYS\n");
215         printf("      -n{numberOfBursts} for setBufferSize\n");
216         printf("      -p{performanceMode} set output AAUDIO_PERFORMANCE_MODE*, default NONE\n");
217         printf("          n for _NONE\n");
218         printf("          l for _LATENCY\n");
219         printf("          p for _POWER_SAVING;\n");
220         printf("      -r{sampleRate} for example 44100\n");
221         printf("      -x to use EXCLUSIVE mode\n");
222     }
223 
parsePerformanceMode(char c)224     static aaudio_performance_mode_t parsePerformanceMode(char c) {
225         aaudio_performance_mode_t mode = AAUDIO_PERFORMANCE_MODE_NONE;
226         switch (c) {
227             case 'n':
228                 mode = AAUDIO_PERFORMANCE_MODE_NONE;
229                 break;
230             case 'l':
231                 mode = AAUDIO_PERFORMANCE_MODE_LOW_LATENCY;
232                 break;
233             case 'p':
234                 mode = AAUDIO_PERFORMANCE_MODE_POWER_SAVING;
235                 break;
236             default:
237                 printf("ERROR invalid performance mode %c\n", c);
238                 break;
239         }
240         return mode;
241     }
242 
243     /**
244      * Print stream parameters in comparison with requested values.
245      * @param stream
246      */
compareWithStream(AAudioStream * stream)247     void compareWithStream(AAudioStream *stream) const {
248 
249         printf("  DeviceId:     requested = %d, actual = %d\n",
250                getDeviceId(), AAudioStream_getDeviceId(stream));
251 
252         aaudio_stream_state_t state = AAudioStream_getState(stream);
253         printf("  State:        %s\n", AAudio_convertStreamStateToText(state));
254 
255         // Check to see what kind of stream we actually got.
256         printf("  SampleRate:   requested = %d, actual = %d\n",
257                getSampleRate(), AAudioStream_getSampleRate(stream));
258 
259         printf("  ChannelCount: requested = %d, actual = %d\n",
260                getChannelCount(), AAudioStream_getChannelCount(stream));
261 
262         printf("  DataFormat:   requested = %d, actual = %d\n",
263                getFormat(), AAudioStream_getFormat(stream));
264 
265         int32_t framesPerBurst = AAudioStream_getFramesPerBurst(stream);
266         int32_t sizeFrames = AAudioStream_getBufferSizeInFrames(stream);
267         printf("  Buffer:       burst     = %d\n", framesPerBurst);
268         if (framesPerBurst > 0) {
269             printf("  Buffer:       size      = %d = (%d * %d) + %d\n",
270                    sizeFrames,
271                    (sizeFrames / framesPerBurst),
272                    framesPerBurst,
273                    (sizeFrames % framesPerBurst));
274         }
275         printf("  Capacity:     requested = %d, actual = %d\n", getBufferCapacity(),
276                AAudioStream_getBufferCapacityInFrames(stream));
277 
278         printf("  SharingMode:  requested = %s, actual = %s\n",
279                getSharingModeText(getSharingMode()),
280                getSharingModeText(AAudioStream_getSharingMode(stream)));
281 
282         printf("  PerformanceMode: requested = %d, actual = %d\n",
283                getPerformanceMode(), AAudioStream_getPerformanceMode(stream));
284         printf("  Is MMAP used? %s\n", AAudioStream_isMMapUsed(stream)
285                ? "yes" : "no");
286 
287     }
288 
getDurationSeconds()289     int32_t getDurationSeconds() const {
290         return mDurationSeconds;
291     }
292 
setDurationSeconds(int32_t seconds)293     void setDurationSeconds(int32_t seconds) {
294         mDurationSeconds = seconds;
295     }
296 
297 private:
298     int32_t      mDurationSeconds = DEFAULT_DURATION_SECONDS;
299 };
300 
301 #endif // AAUDIO_EXAMPLE_ARGS_PARSER_H
302