AudioStream.h revision e2fbb59e729f6c3cade3b531f6f6411417ccbf40
1e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk/*
2e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * Copyright 2016 The Android Open Source Project
3e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk *
4e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * Licensed under the Apache License, Version 2.0 (the "License");
5e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * you may not use this file except in compliance with the License.
6e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * You may obtain a copy of the License at
7e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk *
8e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk *      http://www.apache.org/licenses/LICENSE-2.0
9e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk *
10e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * Unless required by applicable law or agreed to in writing, software
11e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * distributed under the License is distributed on an "AS IS" BASIS,
12e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * See the License for the specific language governing permissions and
14e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk * limitations under the License.
15e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk */
16e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
175ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk#ifndef AAUDIO_AUDIOSTREAM_H
185ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk#define AAUDIO_AUDIOSTREAM_H
19e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
20d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk#include <atomic>
21e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk#include <mutex>
22d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk#include <stdint.h>
235ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk#include <aaudio/AAudio.h>
24d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
25c0c70e3c7dd10bc2c0caffcab1f3f5fb406b35fbPhil Burk#include "utility/AAudioUtilities.h"
26c0c70e3c7dd10bc2c0caffcab1f3f5fb406b35fbPhil Burk#include "utility/MonotonicCounter.h"
27e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
285ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burknamespace aaudio {
29e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
305fbc2ddb4e340d7af02d146ff2e7c3c4da28d535Phil Burktypedef void *(*aaudio_audio_thread_proc_t)(void *);
315fbc2ddb4e340d7af02d146ff2e7c3c4da28d535Phil Burk
32e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burkclass AudioStreamBuilder;
33e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
34e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk/**
355ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk * AAudio audio stream.
36e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk */
37e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burkclass AudioStream {
38e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burkpublic:
39e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
40e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    AudioStream();
41e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
42e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    virtual ~AudioStream();
43e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
44e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
45e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    // =========== Begin ABSTRACT methods ===========================
46e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
47e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    /* Asynchronous requests.
48e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * Use waitForStateChange() to wait for completion.
49e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     */
505ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t requestStart() = 0;
515ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t requestPause() = 0;
525ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t requestFlush() = 0;
535ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t requestStop() = 0;
54e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
555ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t getTimestamp(clockid_t clockId,
563316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk                                       int64_t *framePosition,
573316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk                                       int64_t *timeNanoseconds) = 0;
58e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
59e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
60e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    /**
61e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk     * Update state while in the middle of waitForStateChange()
62e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk     * @return
63e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk     */
64e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    virtual aaudio_result_t updateStateWhileWaiting() = 0;
65e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
66e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
67e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    // =========== End ABSTRACT methods ===========================
68e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
695ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t waitForStateChange(aaudio_stream_state_t currentState,
70e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk                                               aaudio_stream_state_t *nextState,
71e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk                                               int64_t timeoutNanoseconds);
72e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
73e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    /**
74e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * Open the stream using the parameters in the builder.
75e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * Allocate the necessary resources.
76e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     */
775ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t open(const AudioStreamBuilder& builder);
78e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
79e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    /**
80e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * Close the stream and deallocate any resources from the open() call.
81e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * It is safe to call close() multiple times.
82e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     */
835ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t close() {
845ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_OK;
85e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
86e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
873316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual aaudio_result_t setBufferSize(int32_t requestedFrames) {
885ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_ERROR_UNIMPLEMENTED;
89e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
90e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
913316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual aaudio_result_t createThread(int64_t periodNanoseconds,
92e2155ef0ec6742db7a3128c4ef4fb96e02828d1bPhil Burk                                       aaudio_audio_thread_proc_t threadProc,
93d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk                                       void *threadArg);
94e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
953316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual aaudio_result_t joinThread(void **returnArg, int64_t timeoutNanoseconds);
96e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
975ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t registerThread() {
985ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_OK;
99d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    }
100d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
1015ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t unregisterThread() {
1025ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_OK;
103d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    }
104d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
105d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    /**
106d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk     * Internal function used to call the audio thread passed by the user.
107d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk     * It is unfortunately public because it needs to be called by a static 'C' function.
108d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk     */
109d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    void* wrapUserThread();
110d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
111e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    // ============== Queries ===========================
112e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1133316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    aaudio_stream_state_t getState() const {
114e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mState;
115e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
116e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1173316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual int32_t getBufferSize() const {
1185ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_ERROR_UNIMPLEMENTED;
119e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
120e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1213316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual int32_t getBufferCapacity() const {
1225ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_ERROR_UNIMPLEMENTED;
123e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
124e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1253316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual int32_t getFramesPerBurst() const {
1265ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_ERROR_UNIMPLEMENTED;
127e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
128e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
129e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    virtual int32_t getXRunCount() const {
1305ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_ERROR_UNIMPLEMENTED;
131e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
132e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
133e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    bool isPlaying() const {
1345ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return mState == AAUDIO_STREAM_STATE_STARTING || mState == AAUDIO_STREAM_STATE_STARTED;
135e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
136e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
137e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk    virtual bool isMMap() {
138e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk        return false;
139e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk    }
140e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk
1415ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_result_t getSampleRate() const {
142e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mSampleRate;
143e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
144e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1455ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_audio_format_t getFormat()  const {
146e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mFormat;
147e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
148e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1495ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_result_t getSamplesPerFrame() const {
150e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mSamplesPerFrame;
151e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
152e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
153e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk    virtual int32_t getPerformanceMode() const {
154e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk        return mPerformanceMode;
155e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk    }
156e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk
157e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk    void setPerformanceMode(aaudio_performance_mode_t performanceMode) {
158e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk        mPerformanceMode = performanceMode;
159e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk    }
160e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk
1613316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    int32_t getDeviceId() const {
162e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mDeviceId;
163e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
164e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1655ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_sharing_mode_t getSharingMode() const {
166e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mSharingMode;
167e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
168e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
16971f35bb687476694882a617ba4a810a0bb56fe23Phil Burk    bool isSharingModeMatchRequired() const {
17071f35bb687476694882a617ba4a810a0bb56fe23Phil Burk        return mSharingModeMatchRequired;
17171f35bb687476694882a617ba4a810a0bb56fe23Phil Burk    }
17271f35bb687476694882a617ba4a810a0bb56fe23Phil Burk
1735ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_direction_t getDirection() const {
174e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mDirection;
175e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
176e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
177e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    /**
178e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk     * This is only valid after setSamplesPerFrame() and setFormat() have been called.
179e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk     */
1803316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    int32_t getBytesPerFrame() const {
181e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mSamplesPerFrame * getBytesPerSample();
182e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
183e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
184e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    /**
185e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk     * This is only valid after setFormat() has been called.
186e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk     */
1873316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    int32_t getBytesPerSample() const {
1885ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAudioConvert_formatToSizeInBytes(mFormat);
189e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
190e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1913316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual int64_t getFramesWritten() {
192e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mFramesWritten.get();
193e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
194e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
1953316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual int64_t getFramesRead() {
196e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        return mFramesRead.get();
197e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
198e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
199e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    AAudioStream_dataCallback getDataCallbackProc() const {
200e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk        return mDataCallbackProc;
201e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    }
202e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    AAudioStream_errorCallback getErrorCallbackProc() const {
203e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk        return mErrorCallbackProc;
204e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    }
205e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk
206e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    void *getDataCallbackUserData() const {
207e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk        return mDataCallbackUserData;
208e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    }
209e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    void *getErrorCallbackUserData() const {
210e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk        return mErrorCallbackUserData;
211e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    }
212e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk
213e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    int32_t getFramesPerDataCallback() const {
214e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk        return mFramesPerDataCallback;
215e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    }
216e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk
217e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    bool isDataCallbackActive() {
218e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk        return (mDataCallbackProc != nullptr) && isPlaying();
219e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    }
220e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
221e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    // ============== I/O ===========================
222e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    // A Stream will only implement read() or write() depending on its direction.
2235ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t write(const void *buffer,
2243316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk                             int32_t numFrames,
2253316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk                             int64_t timeoutNanoseconds) {
2265ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_ERROR_UNIMPLEMENTED;
227e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
228e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
2295ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    virtual aaudio_result_t read(void *buffer,
2303316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk                            int32_t numFrames,
2313316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk                            int64_t timeoutNanoseconds) {
2325ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk        return AAUDIO_ERROR_UNIMPLEMENTED;
233e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
234e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
235e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burkprotected:
236e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
2373316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual int64_t incrementFramesWritten(int32_t frames) {
2384c5129b410884ec0400cbe65fce56d0ade12d11bPhil Burk        return mFramesWritten.increment(frames);
239e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
240e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
2413316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    virtual int64_t incrementFramesRead(int32_t frames) {
2424c5129b410884ec0400cbe65fce56d0ade12d11bPhil Burk        return mFramesRead.increment(frames);
243e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
244e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
245e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    /**
246e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * This should not be called after the open() call.
247e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     */
2483316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    void setSampleRate(int32_t sampleRate) {
249e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        mSampleRate = sampleRate;
250e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
251e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
252e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    /**
253e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * This should not be called after the open() call.
254e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     */
255e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    void setSamplesPerFrame(int32_t samplesPerFrame) {
256e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        mSamplesPerFrame = samplesPerFrame;
257e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
258e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
259e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    /**
260e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * This should not be called after the open() call.
261e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     */
2625ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    void setSharingMode(aaudio_sharing_mode_t sharingMode) {
263e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        mSharingMode = sharingMode;
264e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
265e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
266e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    /**
267e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     * This should not be called after the open() call.
268e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk     */
2695ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    void setFormat(aaudio_audio_format_t format) {
270e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        mFormat = format;
271e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
272e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
2735ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    void setState(aaudio_stream_state_t state) {
274e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk        mState = state;
275e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    }
276e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
277c0c70e3c7dd10bc2c0caffcab1f3f5fb406b35fbPhil Burk    void setDeviceId(int32_t deviceId) {
278c0c70e3c7dd10bc2c0caffcab1f3f5fb406b35fbPhil Burk        mDeviceId = deviceId;
279c0c70e3c7dd10bc2c0caffcab1f3f5fb406b35fbPhil Burk    }
280c0c70e3c7dd10bc2c0caffcab1f3f5fb406b35fbPhil Burk
281e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    std::mutex           mStreamMutex;
282e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk
283e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    std::atomic<bool>    mCallbackEnabled;
284d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
285d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burkprotected:
286e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    MonotonicCounter     mFramesWritten;
287e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    MonotonicCounter     mFramesRead;
288e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
2893316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    void setPeriodNanoseconds(int64_t periodNanoseconds) {
290d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk        mPeriodNanoseconds.store(periodNanoseconds, std::memory_order_release);
291d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    }
292d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
2933316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    int64_t getPeriodNanoseconds() {
294d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk        return mPeriodNanoseconds.load(std::memory_order_acquire);
295d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    }
296d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
297e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burkprivate:
298e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk    // These do not change after open().
2993316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    int32_t                mSamplesPerFrame = AAUDIO_UNSPECIFIED;
3003316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    int32_t                mSampleRate = AAUDIO_UNSPECIFIED;
3013316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    int32_t                mDeviceId = AAUDIO_UNSPECIFIED;
302c35f3ae6f361a346b6d823601c69dd704afe644aPhil Burk    aaudio_sharing_mode_t  mSharingMode = AAUDIO_SHARING_MODE_SHARED;
30371f35bb687476694882a617ba4a810a0bb56fe23Phil Burk    bool                   mSharingModeMatchRequired = false; // must match sharing mode requested
3045ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_audio_format_t  mFormat = AAUDIO_FORMAT_UNSPECIFIED;
3055ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_direction_t     mDirection = AAUDIO_DIRECTION_OUTPUT;
3063316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    aaudio_stream_state_t  mState = AAUDIO_STREAM_STATE_UNINITIALIZED;
307e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
308e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk    aaudio_performance_mode_t mPerformanceMode = AAUDIO_PERFORMANCE_MODE_NONE;
309e2fbb59e729f6c3cade3b531f6f6411417ccbf40Phil Burk
310e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    // callback ----------------------------------
311e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk
312e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    AAudioStream_dataCallback   mDataCallbackProc = nullptr;  // external callback functions
313e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    void                       *mDataCallbackUserData = nullptr;
314e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    int32_t                     mFramesPerDataCallback = AAUDIO_UNSPECIFIED; // frames
315e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk
316e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    AAudioStream_errorCallback  mErrorCallbackProc = nullptr;
317e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk    void                       *mErrorCallbackUserData = nullptr;
318e4d7bb418df0fdc4c708c334ba3601f5ed8d89b3Phil Burk
319d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    // background thread ----------------------------------
3203316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    bool                   mHasThread = false;
3213316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    pthread_t              mThread; // initialized in constructor
322d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
323d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    // These are set by the application thread and then read by the audio pthread.
3243316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    std::atomic<int64_t>   mPeriodNanoseconds; // for tuning SCHED_FIFO threads
325d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk    // TODO make atomic?
326e2155ef0ec6742db7a3128c4ef4fb96e02828d1bPhil Burk    aaudio_audio_thread_proc_t mThreadProc = nullptr;
3273316d5e6d375a4f09c681205e9094d30a0bfc4a2Phil Burk    void*                  mThreadArg = nullptr;
3285ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk    aaudio_result_t        mThreadRegistrationResult = AAUDIO_OK;
329d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
330d8bdcabbac30d48ed17fa76c83cb9ee95c290a07Phil Burk
331e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk};
332e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
3335ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk} /* namespace aaudio */
334e1ce491a25faf06fdeab00dd938515f71f28b095Phil Burk
3355ed503c7a66c90f93759c90237a9b432dbd93f9fPhil Burk#endif /* AAUDIO_AUDIOSTREAM_H */
336