• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2020 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 ANDROID_PASSTHROUGH_TRACK_TRANSCODER_H
18 #define ANDROID_PASSTHROUGH_TRACK_TRANSCODER_H
19 
20 #include <media/MediaTrackTranscoder.h>
21 #include <media/NdkMediaFormat.h>
22 
23 #include <condition_variable>
24 #include <map>
25 #include <mutex>
26 #include <unordered_map>
27 
28 namespace android {
29 
30 /**
31  * Track transcoder for passthrough mode. Passthrough mode copies sample data from a track unchanged
32  * from source file to destination file. This track transcoder uses an internal pool of buffers.
33  * When the maximum number of buffers are allocated and all of them are waiting on the output queue
34  * the transcoder will stall until samples are dequeued from the output queue and released.
35  */
36 class PassthroughTrackTranscoder : public MediaTrackTranscoder {
37 public:
38     /** Maximum number of buffers to be allocated at a given time. */
39     static constexpr int kMaxBufferCountDefault = 16;
40 
PassthroughTrackTranscoder(const std::weak_ptr<MediaTrackTranscoderCallback> & transcoderCallback)41     PassthroughTrackTranscoder(
42             const std::weak_ptr<MediaTrackTranscoderCallback>& transcoderCallback)
43           : MediaTrackTranscoder(transcoderCallback),
44             mBufferPool(std::make_shared<BufferPool>(kMaxBufferCountDefault)){};
45     virtual ~PassthroughTrackTranscoder() override = default;
46 
47 private:
48     friend class BufferPoolTests;
49 
50     /** Class to pool and reuse buffers. */
51     class BufferPool {
52     public:
BufferPool(int maxBufferCount)53         explicit BufferPool(int maxBufferCount) : mMaxBufferCount(maxBufferCount){};
54         ~BufferPool();
55 
56         /**
57          * Retrieve a buffer from the pool. Buffers are allocated on demand. This method will block
58          * if the maximum number of buffers is reached and there are no free buffers available.
59          * @param minimumBufferSize The minimum size of the buffer.
60          * @return The buffer or nullptr if allocation failed or the pool was aborted.
61          */
62         uint8_t* getBufferWithSize(size_t minimumBufferSize);
63 
64         /**
65          * Return a buffer to the pool.
66          * @param buffer The buffer to return.
67          */
68         void returnBuffer(uint8_t* buffer);
69 
70         /** Wakes up threads waiting on buffers and prevents new buffers from being returned. */
71         void abort();
72 
73     private:
74         // Maximum number of active buffers at a time.
75         const int mMaxBufferCount;
76 
77         // Map containing all tracked buffers.
78         std::unordered_map<uint8_t*, size_t> mAddressSizeMap GUARDED_BY(mMutex);
79 
80         // Map containing the currently free buffers.
81         std::multimap<size_t, uint8_t*> mFreeBufferMap GUARDED_BY(mMutex);
82 
83         std::mutex mMutex;
84         std::condition_variable mCondition;
85         bool mAborted GUARDED_BY(mMutex) = false;
86     };
87 
88     // MediaTrackTranscoder
89     media_status_t runTranscodeLoop(bool* stopped) override;
90     void abortTranscodeLoop() override;
91     media_status_t configureDestinationFormat(
92             const std::shared_ptr<AMediaFormat>& destinationFormat) override;
93     std::shared_ptr<AMediaFormat> getOutputFormat() const override;
94     // ~MediaTrackTranscoder
95 
96     std::shared_ptr<BufferPool> mBufferPool;
97 };
98 
99 }  // namespace android
100 #endif  // ANDROID_PASSTHROUGH_TRACK_TRANSCODER_H
101