TrackBase.h 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358
  1. /*
  2. **
  3. ** Copyright 2012, The Android Open Source Project
  4. **
  5. ** Licensed under the Apache License, Version 2.0 (the "License");
  6. ** you may not use this file except in compliance with the License.
  7. ** You may obtain a copy of the License at
  8. **
  9. ** http://www.apache.org/licenses/LICENSE-2.0
  10. **
  11. ** Unless required by applicable law or agreed to in writing, software
  12. ** distributed under the License is distributed on an "AS IS" BASIS,
  13. ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  14. ** See the License for the specific language governing permissions and
  15. ** limitations under the License.
  16. */
  17. #ifndef INCLUDING_FROM_AUDIOFLINGER_H
  18. #error This header file should only be included from AudioFlinger.h
  19. #endif
  20. // base for record and playback
  21. class TrackBase : public ExtendedAudioBufferProvider, public RefBase {
  22. public:
  23. enum track_state {
  24. IDLE,
  25. FLUSHED, // for PlaybackTracks only
  26. STOPPED,
  27. // next 2 states are currently used for fast tracks
  28. // and offloaded tracks only
  29. STOPPING_1, // waiting for first underrun
  30. STOPPING_2, // waiting for presentation complete
  31. RESUMING, // for PlaybackTracks only
  32. ACTIVE,
  33. PAUSING,
  34. PAUSED,
  35. STARTING_1, // for RecordTrack only
  36. STARTING_2, // for RecordTrack only
  37. };
  38. // where to allocate the data buffer
  39. enum alloc_type {
  40. ALLOC_CBLK, // allocate immediately after control block
  41. ALLOC_READONLY, // allocate from a separate read-only heap per thread
  42. ALLOC_PIPE, // do not allocate; use the pipe buffer
  43. ALLOC_LOCAL, // allocate a local buffer
  44. ALLOC_NONE, // do not allocate:use the buffer passed to TrackBase constructor
  45. };
  46. enum track_type {
  47. TYPE_DEFAULT,
  48. TYPE_OUTPUT,
  49. TYPE_PATCH,
  50. };
  51. TrackBase(ThreadBase *thread,
  52. const sp<Client>& client,
  53. const audio_attributes_t& mAttr,
  54. uint32_t sampleRate,
  55. audio_format_t format,
  56. audio_channel_mask_t channelMask,
  57. size_t frameCount,
  58. void *buffer,
  59. size_t bufferSize,
  60. audio_session_t sessionId,
  61. pid_t creatorPid,
  62. uid_t uid,
  63. bool isOut,
  64. alloc_type alloc = ALLOC_CBLK,
  65. track_type type = TYPE_DEFAULT,
  66. audio_port_handle_t portId = AUDIO_PORT_HANDLE_NONE);
  67. virtual ~TrackBase();
  68. virtual status_t initCheck() const;
  69. virtual status_t start(AudioSystem::sync_event_t event,
  70. audio_session_t triggerSession) = 0;
  71. virtual void stop() = 0;
  72. sp<IMemory> getCblk() const { return mCblkMemory; }
  73. audio_track_cblk_t* cblk() const { return mCblk; }
  74. audio_session_t sessionId() const { return mSessionId; }
  75. uid_t uid() const { return mUid; }
  76. pid_t creatorPid() const { return mCreatorPid; }
  77. audio_port_handle_t portId() const { return mPortId; }
  78. virtual status_t setSyncEvent(const sp<SyncEvent>& event);
  79. sp<IMemory> getBuffers() const { return mBufferMemory; }
  80. void* buffer() const { return mBuffer; }
  81. size_t bufferSize() const { return mBufferSize; }
  82. virtual bool isFastTrack() const = 0;
  83. virtual bool isDirect() const = 0;
  84. bool isOutputTrack() const { return (mType == TYPE_OUTPUT); }
  85. bool isPatchTrack() const { return (mType == TYPE_PATCH); }
  86. bool isExternalTrack() const { return !isOutputTrack() && !isPatchTrack(); }
  87. virtual void invalidate() { mIsInvalid = true; }
  88. bool isInvalid() const { return mIsInvalid; }
  89. void terminate() { mTerminated = true; }
  90. bool isTerminated() const { return mTerminated; }
  91. audio_attributes_t attributes() const { return mAttr; }
  92. #ifdef TEE_SINK
  93. void dumpTee(int fd, const std::string &reason) const {
  94. mTee.dump(fd, reason);
  95. }
  96. #endif
  97. /** returns the buffer contents size converted to time in milliseconds
  98. * for PCM Playback or Record streaming tracks. The return value is zero for
  99. * PCM static tracks and not defined for non-PCM tracks.
  100. *
  101. * This may be called without the thread lock.
  102. */
  103. virtual double bufferLatencyMs() const {
  104. return mServerProxy->framesReadySafe() * 1000 / sampleRate();
  105. }
  106. /** returns whether the track supports server latency computation.
  107. * This is set in the constructor and constant throughout the track lifetime.
  108. */
  109. bool isServerLatencySupported() const { return mServerLatencySupported; }
  110. /** computes the server latency for PCM Playback or Record track
  111. * to the device sink/source. This is the time for the next frame in the track buffer
  112. * written or read from the server thread to the device source or sink.
  113. *
  114. * This may be called without the thread lock, but latencyMs and fromTrack
  115. * may be not be synchronized. For example PatchPanel may not obtain the
  116. * thread lock before calling.
  117. *
  118. * \param latencyMs on success is set to the latency in milliseconds of the
  119. * next frame written/read by the server thread to/from the track buffer
  120. * from the device source/sink.
  121. * \param fromTrack on success is set to true if latency was computed directly
  122. * from the track timestamp; otherwise set to false if latency was
  123. * estimated from the server timestamp.
  124. * fromTrack may be nullptr or omitted if not required.
  125. *
  126. * \returns OK or INVALID_OPERATION on failure.
  127. */
  128. status_t getServerLatencyMs(double *latencyMs, bool *fromTrack = nullptr) const {
  129. if (!isServerLatencySupported()) {
  130. return INVALID_OPERATION;
  131. }
  132. // if no thread lock is acquired, these atomics are not
  133. // synchronized with each other, considered a benign race.
  134. const double serverLatencyMs = mServerLatencyMs.load();
  135. if (serverLatencyMs == 0.) {
  136. return INVALID_OPERATION;
  137. }
  138. if (fromTrack != nullptr) {
  139. *fromTrack = mServerLatencyFromTrack.load();
  140. }
  141. *latencyMs = serverLatencyMs;
  142. return OK;
  143. }
  144. /** computes the total client latency for PCM Playback or Record tracks
  145. * for the next client app access to the device sink/source; i.e. the
  146. * server latency plus the buffer latency.
  147. *
  148. * This may be called without the thread lock, but latencyMs and fromTrack
  149. * may be not be synchronized. For example PatchPanel may not obtain the
  150. * thread lock before calling.
  151. *
  152. * \param latencyMs on success is set to the latency in milliseconds of the
  153. * next frame written/read by the client app to/from the track buffer
  154. * from the device sink/source.
  155. * \param fromTrack on success is set to true if latency was computed directly
  156. * from the track timestamp; otherwise set to false if latency was
  157. * estimated from the server timestamp.
  158. * fromTrack may be nullptr or omitted if not required.
  159. *
  160. * \returns OK or INVALID_OPERATION on failure.
  161. */
  162. status_t getTrackLatencyMs(double *latencyMs, bool *fromTrack = nullptr) const {
  163. double serverLatencyMs;
  164. status_t status = getServerLatencyMs(&serverLatencyMs, fromTrack);
  165. if (status == OK) {
  166. *latencyMs = serverLatencyMs + bufferLatencyMs();
  167. }
  168. return status;
  169. }
  170. // TODO: Consider making this external.
  171. struct FrameTime {
  172. int64_t frames;
  173. int64_t timeNs;
  174. };
  175. // KernelFrameTime is updated per "mix" period even for non-pcm tracks.
  176. void getKernelFrameTime(FrameTime *ft) const {
  177. *ft = mKernelFrameTime.load();
  178. }
  179. audio_format_t format() const { return mFormat; }
  180. int id() const { return mId; }
  181. protected:
  182. DISALLOW_COPY_AND_ASSIGN(TrackBase);
  183. // AudioBufferProvider interface
  184. virtual status_t getNextBuffer(AudioBufferProvider::Buffer* buffer) = 0;
  185. virtual void releaseBuffer(AudioBufferProvider::Buffer* buffer);
  186. // ExtendedAudioBufferProvider interface is only needed for Track,
  187. // but putting it in TrackBase avoids the complexity of virtual inheritance
  188. virtual size_t framesReady() const { return SIZE_MAX; }
  189. uint32_t channelCount() const { return mChannelCount; }
  190. size_t frameSize() const { return mFrameSize; }
  191. audio_channel_mask_t channelMask() const { return mChannelMask; }
  192. virtual uint32_t sampleRate() const { return mSampleRate; }
  193. bool isStopped() const {
  194. return (mState == STOPPED || mState == FLUSHED);
  195. }
  196. // for fast tracks and offloaded tracks only
  197. bool isStopping() const {
  198. return mState == STOPPING_1 || mState == STOPPING_2;
  199. }
  200. bool isStopping_1() const {
  201. return mState == STOPPING_1;
  202. }
  203. bool isStopping_2() const {
  204. return mState == STOPPING_2;
  205. }
  206. // Upper case characters are final states.
  207. // Lower case characters are transitory.
  208. const char *getTrackStateString() const {
  209. if (isTerminated()) {
  210. return "T ";
  211. }
  212. switch (mState) {
  213. case IDLE:
  214. return "I ";
  215. case STOPPING_1: // for Fast and Offload
  216. return "s1";
  217. case STOPPING_2: // for Fast and Offload
  218. return "s2";
  219. case STOPPED:
  220. return "S ";
  221. case RESUMING:
  222. return "r ";
  223. case ACTIVE:
  224. return "A ";
  225. case PAUSING:
  226. return "p ";
  227. case PAUSED:
  228. return "P ";
  229. case FLUSHED:
  230. return "F ";
  231. case STARTING_1: // for RecordTrack
  232. return "r1";
  233. case STARTING_2: // for RecordTrack
  234. return "r2";
  235. default:
  236. return "? ";
  237. }
  238. }
  239. bool isOut() const { return mIsOut; }
  240. // true for Track, false for RecordTrack,
  241. // this could be a track type if needed later
  242. const wp<ThreadBase> mThread;
  243. /*const*/ sp<Client> mClient; // see explanation at ~TrackBase() why not const
  244. sp<IMemory> mCblkMemory;
  245. audio_track_cblk_t* mCblk;
  246. sp<IMemory> mBufferMemory; // currently non-0 for fast RecordTrack only
  247. void* mBuffer; // start of track buffer, typically in shared memory
  248. // except for OutputTrack when it is in local memory
  249. size_t mBufferSize; // size of mBuffer in bytes
  250. // we don't really need a lock for these
  251. track_state mState;
  252. const audio_attributes_t mAttr;
  253. const uint32_t mSampleRate; // initial sample rate only; for tracks which
  254. // support dynamic rates, the current value is in control block
  255. const audio_format_t mFormat;
  256. const audio_channel_mask_t mChannelMask;
  257. const uint32_t mChannelCount;
  258. const size_t mFrameSize; // AudioFlinger's view of frame size in shared memory,
  259. // where for AudioTrack (but not AudioRecord),
  260. // 8-bit PCM samples are stored as 16-bit
  261. const size_t mFrameCount;// size of track buffer given at createTrack() or
  262. // createRecord(), and then adjusted as needed
  263. const audio_session_t mSessionId;
  264. uid_t mUid;
  265. Vector < sp<SyncEvent> >mSyncEvents;
  266. const bool mIsOut;
  267. sp<ServerProxy> mServerProxy;
  268. const int mId;
  269. #ifdef TEE_SINK
  270. NBAIO_Tee mTee;
  271. #endif
  272. bool mTerminated;
  273. track_type mType; // must be one of TYPE_DEFAULT, TYPE_OUTPUT, TYPE_PATCH ...
  274. audio_io_handle_t mThreadIoHandle; // I/O handle of the thread the track is attached to
  275. audio_port_handle_t mPortId; // unique ID for this track used by audio policy
  276. bool mIsInvalid; // non-resettable latch, set by invalidate()
  277. bool mServerLatencySupported = false;
  278. std::atomic<bool> mServerLatencyFromTrack{}; // latency from track or server timestamp.
  279. std::atomic<double> mServerLatencyMs{}; // last latency pushed from server thread.
  280. std::atomic<FrameTime> mKernelFrameTime{}; // last frame time on kernel side.
  281. const pid_t mCreatorPid; // can be different from mclient->pid() for instance
  282. // when created by NuPlayer on behalf of a client
  283. };
  284. // PatchProxyBufferProvider interface is implemented by PatchTrack and PatchRecord.
  285. // it provides buffer access methods that map those of a ClientProxy (see AudioTrackShared.h)
  286. class PatchProxyBufferProvider
  287. {
  288. public:
  289. virtual ~PatchProxyBufferProvider() {}
  290. virtual status_t obtainBuffer(Proxy::Buffer* buffer,
  291. const struct timespec *requested = NULL) = 0;
  292. virtual void releaseBuffer(Proxy::Buffer* buffer) = 0;
  293. };
  294. class PatchTrackBase : public PatchProxyBufferProvider
  295. {
  296. public:
  297. using Timeout = std::optional<std::chrono::nanoseconds>;
  298. PatchTrackBase(sp<ClientProxy> proxy, const ThreadBase& thread,
  299. const Timeout& timeout);
  300. void setPeerTimeout(std::chrono::nanoseconds timeout);
  301. template <typename T>
  302. void setPeerProxy(const sp<T> &proxy, bool holdReference) {
  303. mPeerReferenceHold = holdReference ? proxy : nullptr;
  304. mPeerProxy = proxy.get();
  305. }
  306. void clearPeerProxy() {
  307. mPeerReferenceHold.clear();
  308. mPeerProxy = nullptr;
  309. }
  310. protected:
  311. const sp<ClientProxy> mProxy;
  312. sp<RefBase> mPeerReferenceHold; // keeps mPeerProxy alive during access.
  313. PatchProxyBufferProvider* mPeerProxy = nullptr;
  314. struct timespec mPeerTimeout{};
  315. };