1 /*
2 * Copyright (c) 2015 Intel Corporation.  All rights reserved.
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 
18 #ifndef MEDIA_RESOURCE_ARBITRATOR_H_
19 #define MEDIA_RESOURCE_ARBITRATOR_H_
20 
21 #include <unistd.h>
22 #include <string.h>
23 #include <utils/KeyedVector.h>
24 #include <utils/Vector.h>
25 
26 #define MAX_BUFFER_SIZE (20 * 1024)
27 
28 using namespace android;
29 
30 // This error type keeps align with the OMX error type
31 typedef enum _ArbitratorErrorType {
32     ArbitratorErrorNone = 0,
33 
34     /** There were insufficient resources to perform the requested operation */
35     ArbitratorErrorInsufficientResources = 0x80001000,
36 
37     /** There was an error, but the cause of the error could not be determined */
38     ArbitratorErrorUndefined = 0x80001001
39 } ArbitratorErrorType;
40 
41 
42 typedef enum _ResolutionType {
43     Resolution_CIF = 0,
44     Resolution_480,
45     Resolution_720,
46     Resolution_1080,
47     Resolution_2K,
48     Resolution_4K,
49     Resolution_MAX
50 } ResolutionType;
51 
52 
53 typedef enum _CodecType {
54     CODEC_TYPE_AVC = 0,
55     CODEC_TYPE_HEVC,
56     CODEC_TYPE_VP8,
57     CODEC_TYPE_VP9,
58     CODEC_TYPE_MPEG4,
59     CODEC_TYPE_MPEG2,
60     CODEC_TYPE_H263,
61     CODEC_TYPE_VC1,
62     CODEC_TYPE_WMV,
63     CODEC_TYPE_MAX
64 } CodecType;
65 
66 
67 typedef struct _CodecInfo {
68     CodecType codecType;
69     bool isEncoder;
70     bool isSecured;
71     ResolutionType resolution;
72     uint frameRate;
73 } CodecInfo;
74 
75 
76 typedef struct _CodecLimitInfo {
77     CodecInfo codecInfo;
78     int instanceLimit;
79 } CodecLimitInfo;
80 
81 
82 typedef struct _LivingDecodersTable {
83     Vector<CodecInfo> livingDecoders;
84     uint maxResolution;
85     uint maxFrameRate;
86 } LivingDecodersTable;
87 
88 
89 typedef struct _LivingEncodersTable {
90     Vector<CodecInfo> livingEncoders;
91     uint maxResolution;
92     uint maxFrameRate;
93 } LivingEncodersTable;
94 
95 
96 class MediaResourceArbitrator {
97 public:
98     MediaResourceArbitrator ();
99     ~MediaResourceArbitrator ();
100 
101     /* Initialize the arbitrator.
102        Parse the config XML file if given. */
103     ArbitratorErrorType Config(const char* configFilePath);
104 
105     /* Check if the resource limitation is hit and
106        it is under full load status. In such status, there
107        is no room to instantiate codec anymore. */
108     bool CheckIfFullLoad(bool isEncoder);
109 
110     /* Add codec in the pool.
111        Resolution and frame rate must be provided.
112        This is not necessarily be called when codec instance
113        is constructed when the resolution and frame rate are
114        not known yet.
115        This may be called when codec is configured,
116        for example in OMX set parameter, etc.
117        Return value is expected to be as one of:
118            ArbitratorErrorNone,
119            ArbitratorErrorInsufficientResources
120      */
121     ArbitratorErrorType AddResource(/* in */  CodecType codecType,
122                                     /* in */  bool isEncoder,
123                                     /* in */  bool isSecured,
124                                     /* in */  ResolutionType resolution,
125                                     /* in */  uint frameRate);
126 
127     /* Remove codec in the pool.*/
128     ArbitratorErrorType RemoveResource(CodecType codecType,
129                                        bool isEncoder,
130                                        bool isSecured,
131                                        ResolutionType resolution,
132                                        uint frameRate);
133 
134     uint GetLivingCodecsNum(void);
135 
136     // XML function
137     void ParseXMLFile(FILE* fp);
138     static void startElement(void *userData, const char *name, const char **atts);
139     static void endElement(void *userData, const char *name);
140     void getConfigData(const char *name, const char **atts);
141 
142 private:
143     // a global table stores all codec limit info
144     Vector<CodecLimitInfo> mDecoderLimitInfos;
145     Vector<CodecLimitInfo> mEncoderLimitInfos;
146 
147     // a global talbe stores all living codec info
148     LivingDecodersTable mLivingDecodersTable;
149     LivingEncodersTable mLivingEncodersTable;
150 
151     // arbitrator lock
152     pthread_mutex_t mArbitratorLock;
153 
154     // indicate whether it is under full load status
155     bool mIsEncoderUnderFullLoad;
156     bool mIsDecoderUnderFullLoad;
157 
158     KeyedVector <const char*, CodecType> mCodecNameTypeMap;
159     KeyedVector <const char*, ResolutionType> mResolutionNameTypeMap;
160 
161     static const int mBufSize = MAX_BUFFER_SIZE;
162     // indicate XML parser is parsing a codec tag
163     bool mIfParsingCodec;
164     CodecLimitInfo mParsingCodecLimitInfo;
165 
166     ArbitratorErrorType ArbitrateFullLoad(CodecInfo& codec);
167 
168     bool CheckCodecMatched(const CodecInfo& sourceCodec,
169                            const CodecInfo& targetCodec);
170 
171     void SetupDefaultCodecLimitation(void);
172     void InitializeCodecNameTypeMap();
173     void InitializeResolutionNameTypeMap();
174     void DumpCodecTypeFromVector(void);
175     CodecType MapCodecTypeFromName(const char* name);
176     ResolutionType MapResolutionTypeFromName(const char* name);
177 };
178 
179 #endif /* MEDIA_RESOURCE_ARBITRATOR_H_ */
180