1 /*
2  * Copyright (C) 2016 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 STAGEFRIGHT_CODEC2_ALLOCATOR_ION_H_
18 #define STAGEFRIGHT_CODEC2_ALLOCATOR_ION_H_
19 
20 #include <functional>
21 #include <list>
22 #include <mutex>
23 #include <tuple>
24 #include <unordered_map>
25 
26 #include <C2Buffer.h>
27 
28 namespace android {
29 
30 class C2AllocatorIon : public C2Allocator {
31 public:
32     // Usage mapper function used by the allocator
33     //   (usage, capacity) => (align, heapMask, flags)
34     //
35     // capacity is aligned to the default block-size (defaults to page size) to reduce caching
36     // overhead
37     typedef std::function<c2_status_t(C2MemoryUsage, size_t,
38                       /* => */ size_t*, unsigned*, unsigned*)> UsageMapperFn;
39 
40     virtual id_t getId() const override;
41 
42     virtual C2String getName() const override;
43 
44     virtual std::shared_ptr<const Traits> getTraits() const override;
45 
46     virtual c2_status_t newLinearAllocation(
47             uint32_t capacity, C2MemoryUsage usage,
48             std::shared_ptr<C2LinearAllocation> *allocation) override;
49 
50     virtual c2_status_t priorLinearAllocation(
51             const C2Handle *handle,
52             std::shared_ptr<C2LinearAllocation> *allocation) override;
53 
54     C2AllocatorIon(id_t id);
55 
status()56     virtual c2_status_t status() const { return mInit; }
57 
58     virtual ~C2AllocatorIon() override;
59 
checkHandle(const C2Handle * const o)60     virtual bool checkHandle(const C2Handle* const o) const override { return CheckHandle(o); }
61 
62     static bool CheckHandle(const C2Handle* const o);
63 
64     // deprecated
isValid(const C2Handle * const o)65     static bool isValid(const C2Handle* const o) { return CheckHandle(o); }
66 
67     /**
68      * Updates the usage mapper for subsequent new allocations, as well as the supported
69      * minimum and maximum usage masks and default block-size to use for the mapper.
70      *
71      * \param mapper this method is called to map Codec 2.0 buffer usage to ion flags
72      *        required by the ion device
73      * \param minUsage minimum buffer usage required for supported allocations (defaults to 0)
74      * \param maxUsage maximum buffer usage supported by the ion allocator (defaults to SW_READ
75      *        | SW_WRITE)
76      * \param blockSize alignment used prior to calling |mapper| for the buffer capacity.
77      *        This also helps reduce the size of cache required for caching mapper results.
78      *        (defaults to the page size)
79      */
80     void setUsageMapper(
81             const UsageMapperFn &mapper, uint64_t minUsage, uint64_t maxUsage, uint64_t blockSize);
82 
83 private:
84     c2_status_t mapUsage(C2MemoryUsage usage, size_t size,
85                      /* => */ size_t *align, unsigned *heapMask, unsigned *flags);
86 
87     c2_status_t mInit;
88     int mIonFd;
89 
90     // this locks mTraits, mBlockSize, mUsageMapper, mUsageMapperLru and mUsageMapperCache
91     mutable std::mutex mUsageMapperLock;
92     std::shared_ptr<const Traits> mTraits;
93     size_t mBlockSize;
94     UsageMapperFn mUsageMapper;
95     typedef std::pair<uint64_t, size_t> MapperKey;
96     struct MapperKeyHash {
97         std::size_t operator()(const MapperKey &) const;
98     };
99     typedef std::tuple<size_t, unsigned, unsigned, c2_status_t> MapperValue;
100     typedef std::pair<MapperKey, MapperValue> MapperKeyValue;
101     typedef std::list<MapperKeyValue>::iterator MapperKeyValuePointer;
102     std::list<MapperKeyValue> mUsageMapperLru;
103     std::unordered_map<MapperKey, MapperKeyValuePointer, MapperKeyHash> mUsageMapperCache;
104 };
105 
106 } // namespace android
107 
108 #endif // STAGEFRIGHT_CODEC2_ALLOCATOR_ION_H_
109