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_AAUDIO_SERVICE_STREAM_MMAP_H 18#define AAUDIO_AAUDIO_SERVICE_STREAM_MMAP_H 19 20#include <atomic> 21 22#include <media/audiohal/StreamHalInterface.h> 23#include <media/MmapStreamCallback.h> 24#include <media/MmapStreamInterface.h> 25#include <utils/RefBase.h> 26#include <utils/String16.h> 27#include <utils/Vector.h> 28 29#include "binding/AAudioServiceMessage.h" 30#include "AAudioServiceStreamBase.h" 31#include "binding/AudioEndpointParcelable.h" 32#include "SharedMemoryProxy.h" 33#include "TimestampScheduler.h" 34#include "utility/MonotonicCounter.h" 35 36namespace aaudio { 37 38 /** 39 * Manage one memory mapped buffer that originated from a HAL. 40 */ 41class AAudioServiceStreamMMAP 42 : public AAudioServiceStreamBase 43 , public android::MmapStreamCallback { 44 45public: 46 AAudioServiceStreamMMAP(); 47 virtual ~AAudioServiceStreamMMAP(); 48 49 50 aaudio_result_t open(const aaudio::AAudioStreamRequest &request, 51 aaudio::AAudioStreamConfiguration &configurationOutput) override; 52 53 /** 54 * Start the flow of audio data. 55 * 56 * This is not guaranteed to be synchronous but it currently is. 57 * An AAUDIO_SERVICE_EVENT_STARTED will be sent to the client when complete. 58 */ 59 aaudio_result_t start() override; 60 61 /** 62 * Stop the flow of data so that start() can resume without loss of data. 63 * 64 * This is not guaranteed to be synchronous but it currently is. 65 * An AAUDIO_SERVICE_EVENT_PAUSED will be sent to the client when complete. 66 */ 67 aaudio_result_t pause() override; 68 69 aaudio_result_t stop() override; 70 71 /** 72 * Discard any data held by the underlying HAL or Service. 73 * 74 * This is not guaranteed to be synchronous but it currently is. 75 * An AAUDIO_SERVICE_EVENT_FLUSHED will be sent to the client when complete. 76 */ 77 aaudio_result_t flush() override; 78 79 aaudio_result_t close() override; 80 81 /** 82 * Send a MMAP/NOIRQ buffer timestamp to the client. 83 */ 84 aaudio_result_t sendCurrentTimestamp(); 85 86 // -------------- Callback functions --------------------- 87 void onTearDown() override; 88 89 void onVolumeChanged(audio_channel_mask_t channels, 90 android::Vector<float> values) override; 91 92 void onRoutingChanged(audio_port_handle_t deviceId) override; 93 94protected: 95 96 aaudio_result_t getDownDataDescription(AudioEndpointParcelable &parcelable) override; 97 98 aaudio_result_t getFreeRunningPosition(int64_t *positionFrames, int64_t *timeNanos) override; 99 100private: 101 // This proxy class was needed to prevent a crash in AudioFlinger 102 // when the stream was closed. 103 class MyMmapStreamCallback : public android::MmapStreamCallback { 104 public: 105 explicit MyMmapStreamCallback(android::MmapStreamCallback &serviceCallback) 106 : mServiceCallback(serviceCallback){} 107 virtual ~MyMmapStreamCallback() = default; 108 109 void onTearDown() override { 110 mServiceCallback.onTearDown(); 111 }; 112 113 void onVolumeChanged(audio_channel_mask_t channels, android::Vector<float> values) override 114 { 115 mServiceCallback.onVolumeChanged(channels, values); 116 }; 117 118 void onRoutingChanged(audio_port_handle_t deviceId) override { 119 mServiceCallback.onRoutingChanged(deviceId); 120 }; 121 122 private: 123 android::MmapStreamCallback &mServiceCallback; 124 }; 125 126 android::sp<MyMmapStreamCallback> mMmapStreamCallback; 127 MonotonicCounter mFramesWritten; 128 MonotonicCounter mFramesRead; 129 int32_t mPreviousFrameCounter = 0; // from HAL 130 int mAudioDataFileDescriptor = -1; 131 132 // Interface to the AudioFlinger MMAP support. 133 android::sp<android::MmapStreamInterface> mMmapStream; 134 struct audio_mmap_buffer_info mMmapBufferinfo; 135 android::MmapStreamInterface::Client mMmapClient; 136 audio_port_handle_t mPortHandle = -1; // TODO review best default 137}; 138 139} // namespace aaudio 140 141#endif //AAUDIO_AAUDIO_SERVICE_STREAM_MMAP_H 142