• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #include "avcodec_xml_parser.h"
16 #include "media_errors.h"
17 #include "media_log.h"
18 #include "string_ex.h"
19 
20 namespace {
21     constexpr OHOS::HiviewDFX::HiLogLabel LABEL = {LOG_CORE, LOG_DOMAIN, "AVCodecXmlParser"};
22     constexpr int32_t PAIR_LENGTH = 2;
23     const std::string AVCODEC_CONFIG_FILE = "/etc/codec/codec_caps.xml";
24 }
25 
26 namespace OHOS {
27 namespace Media {
28 const std::unordered_map<std::string, int> VIDEO_PROFILE_MAP = {
29     // H263
30     {"H263BackwardCompatible", H263_PROFILE_BACKWARD_COMPATIBLE},
31     {"H263Baseline", H263_PROFILE_BASELINE},
32     {"H263H320Coding", H263_PROFILE_H320_CODING},
33     {"H263HighCompression", H263_PROFILE_HIGH_COMPRESSION},
34     {"H263HighLatency", H263_PROFILE_HIGH_LATENCY},
35     {"H263ISWV2", H263_PROFILE_ISW_V2},
36     {"H263ISWV3", H263_PROFILE_ISW_V3},
37     {"H263Interlace", H263_PROFILE_INTERLACE},
38     {"H263Internet", H263_PROFILE_INTERNET},
39     // H264
40     {"AVCBaseline", AVC_PROFILE_BASELINE},
41     {"AVCHighCompression", AVC_PROFILE_CONSTRAINED_BASELINE},
42     {"AVCConstrainedHigh", AVC_PROFILE_CONSTRAINED_HIGH},
43     {"AVCExtended", AVC_PROFILE_EXTENDED},
44     {"AVCHigh", AVC_PROFILE_HIGH},
45     {"AVCHigh10", AVC_PROFILE_HIGH_10},
46     {"AVCHigh422", AVC_PROFILE_HIGH_422},
47     {"AVCHigh444", AVC_PROFILE_HIGH_444},
48     {"AVCMain", AVC_PROFILE_MAIN},
49     // H265
50     {"HEVCMain", HEVC_PROFILE_MAIN},
51     {"HEVCMain10", HEVC_PROFILE_MAIN_10},
52     {"HEVCMainStill", HEVC_PROFILE_MAIN_STILL},
53     // MPEG2
54     {"MPEG2_422", MPEG2_PROFILE_422},
55     {"MPEG2High", MPEG2_PROFILE_HIGH},
56     {"MPEG2Main", MPEG2_PROFILE_MAIN},
57     {"MPEG2SNR", MPEG2_PROFILE_SNR},
58     {"MPEG2Simple", MPEG2_PROFILE_SIMPLE},
59     {"MPEG2Spatial", MPEG2_PROFILE_SPATIAL},
60     // MPEG4
61     {"MPEG4AdvancedCoding", MPEG4_PROFILE_ADVANCED_CODING},
62     {"MPEG4AdvancedCore", MPEG4_PROFILE_ADVANCED_CORE},
63     {"MPEG4AdvancedRealTime", MPEG4_PROFILE_ADVANCED_REAL_TIME},
64     {"MPEG4AdvancedScalable", MPEG4_PROFILE_ADVANCED_SCALABLE},
65     {"MPEG4AdvancedSimple", MPEG4_PROFILE_ADVANCED_SIMPLE},
66     {"MPEG4BasicAnimated", MPEG4_PROFILE_BASIC_ANIMATED},
67     {"MPEG4Core", MPEG4_PROFILE_CORE},
68     {"MPEG4CoreScalable", MPEG4_PROFILE_CORE_SCALABLE},
69     {"MPEG4Hybrid", MPEG4_PROFILE_HYBRID},
70     {"MPEG4Main", MPEG4_PROFILE_MAIN},
71     {"MPEG4Nbit", MPEG4_PROFILE_NBIT},
72     {"MPEG4ScalableTexture", MPEG4_PROFILE_SCALABLE_TEXTURE},
73     {"MPEG4Simple", MPEG4_PROFILE_SIMPLE},
74     {"MPEG4SimpleFBA", MPEG4_PROFILE_SIMPLE_FBA},
75     {"MPEG4SimpleFace", MPEG4_PROFILE_SIMPLE_FACE},
76     {"MPEG4SimpleScalable", MPEG4_PROFILE_SIMPLE_SCALABLE},
77     // VP8
78     {"VP8Main", VP8_PROFILE_MAIN},
79 };
80 
81 const std::unordered_map<std::string, int> AUDIO_PROFILE_MAP = {
82     {"AAC_LC", AAC_PROFILE_LC},
83     {"AAC_ELD", AAC_PROFILE_ELD},
84     {"AAC_ERLC", AAC_PROFILE_ERLC},
85     {"AAC_HE", AAC_PROFILE_HE},
86     {"AAC_HE_V2", AAC_PROFILE_HE_V2},
87     {"AAC_LD", AAC_PROFILE_LD},
88     {"AAC_Main", AAC_PROFILE_MAIN},
89 };
90 
91 const std::unordered_map<std::string, int> VIDEO_FORMAT_MAP = {
92     {"YUVI420", YUVI420},
93     {"NV12", NV12},
94     {"NV21", NV21},
95     {"RGBA", RGBA},
96 };
97 
98 const std::unordered_map<std::string, int> AUDIO_FORMAT_MAP = {
99     {"U8", AudioStandard::SAMPLE_U8},
100     {"S16LE", AudioStandard::SAMPLE_S16LE},
101     {"S24LE", AudioStandard::SAMPLE_S24LE},
102     {"S32LE", AudioStandard::SAMPLE_S32LE},
103 };
104 
105 const std::unordered_map<std::string, int> BITRATE_MODE_MAP = {
106     {"CBR", CBR},
107     {"VBR", VBR},
108     {"CQ", CQ},
109 };
110 
111 const std::unordered_map<std::string, AVCodecType> CODEC_TYPE_MAP = {
112     {"VIDEO_ENCODER", AVCODEC_TYPE_VIDEO_ENCODER},
113     {"VIDEO_DECODER", AVCODEC_TYPE_VIDEO_DECODER},
114     {"AUDIO_ENCODER", AVCODEC_TYPE_AUDIO_ENCODER},
115     {"AUDIO_DECODER", AVCODEC_TYPE_AUDIO_DECODER},
116 };
117 
AVCodecXmlParser()118 AVCodecXmlParser::AVCodecXmlParser()
119 {
120     capabilityKeys_ = {
121         "codecName",
122         "codecType",
123         "mimeType",
124         "isVendor",
125         "bitrate",
126         "channels",
127         "sampleRate",
128         "format",
129         "profiles",
130         "complexity",
131         "bitrateMode",
132         "alignment",
133         "width",
134         "height",
135         "frameRate",
136         "encodeQuality",
137         "quality",
138         "levels",
139         "blockPerFrame",
140         "blockPerSecond",
141         "blockSize",
142         "profileLevelsMap",
143         "measuredFrameRate",
144     };
145     MEDIA_LOGD("0x%{public}06" PRIXPTR " Instances create", FAKE_POINTER(this));
146 }
147 
~AVCodecXmlParser()148 AVCodecXmlParser::~AVCodecXmlParser()
149 {
150     Destroy();
151     MEDIA_LOGD("0x%{public}06" PRIXPTR " Instances destroy", FAKE_POINTER(this));
152 }
153 
LoadConfiguration()154 bool AVCodecXmlParser::LoadConfiguration()
155 {
156     mDoc_ = xmlReadFile(AVCODEC_CONFIG_FILE.c_str(), nullptr, 0);
157     if (mDoc_ == nullptr) {
158         MEDIA_LOGE("AVCodec xmlReadFile failed");
159         return false;
160     }
161     return true;
162 }
163 
Parse()164 bool AVCodecXmlParser::Parse()
165 {
166     xmlNode *root = xmlDocGetRootElement(mDoc_);
167     if (root == nullptr) {
168         MEDIA_LOGE("AVCodec xmlDocGetRootElement failed");
169         return false;
170     }
171     return ParseInternal(root);
172 }
173 
Destroy()174 void AVCodecXmlParser::Destroy()
175 {
176     if (mDoc_ != nullptr) {
177         xmlFreeDoc(mDoc_);
178     }
179     return;
180 }
181 
ParseInternal(xmlNode * node)182 bool AVCodecXmlParser::ParseInternal(xmlNode *node)
183 {
184     xmlNode *currNode = node;
185     for (; currNode != nullptr; currNode = currNode->next) {
186         if (currNode->type == XML_ELEMENT_NODE) {
187             switch (GetNodeNameAsInt(currNode)) {
188                 case AUDIO_DECODER:
189                 case AUDIO_ENCODER:
190                 case VIDEO_DECODER:
191                 case VIDEO_ENCODER: {
192                     ParseData(currNode);
193                     break;
194                 }
195                 default:
196                     ParseInternal(currNode->children);
197                     break;
198             }
199         }
200     }
201     return true;
202 }
203 
TransStrAsRange(const std::string & str,Range & range)204 bool AVCodecXmlParser::TransStrAsRange(const std::string &str, Range &range)
205 {
206     if (str == "null" || str == "") {
207         MEDIA_LOGD("str is null");
208         return false;
209     }
210     size_t pos = str.find("-");
211     if (pos != str.npos && pos + 1 < str.size()) {
212         std::string head = str.substr(0, pos);
213         std::string tail = str.substr(pos + 1);
214         if (!StrToInt(head, range.minVal)) {
215             MEDIA_LOGE("call StrToInt func false, input str is: %{public}s", head.c_str());
216             return false;
217         }
218         if (!StrToInt(tail, range.maxVal)) {
219             MEDIA_LOGE("call StrToInt func false, input str is: %{public}s", tail.c_str());
220             return false;
221         }
222     } else {
223         MEDIA_LOGD("Can not find the delimiter of \"-\" in : %{public}s", str.c_str());
224         return false;
225     }
226     return true;
227 }
228 
TransStrAsSize(const std::string & str,ImgSize & size)229 bool AVCodecXmlParser::TransStrAsSize(const std::string &str, ImgSize &size)
230 {
231     if (str == "null" || str == "") {
232         MEDIA_LOGD("str is null");
233         return false;
234     }
235     size_t pos = str.find("x");
236     if (pos != str.npos && pos + 1 < str.size()) {
237         std::string head = str.substr(0, pos);
238         std::string tail = str.substr(pos + 1);
239         if (!StrToInt(head, size.width)) {
240             MEDIA_LOGE("call StrToInt func false, input str is: %{public}s", head.c_str());
241             return false;
242         }
243         if (!StrToInt(tail, size.height)) {
244             MEDIA_LOGE("call StrToInt func false, input str is: %{public}s", tail.c_str());
245             return false;
246         }
247     } else {
248         MEDIA_LOGD("Can not find the delimiter of \"x\" in : %{public}s", str.c_str());
249         return false;
250     }
251     return true;
252 }
253 
TransStrAsIntegerArray(const std::vector<std::string> & spilt)254 std::vector<int32_t> AVCodecXmlParser::TransStrAsIntegerArray(const std::vector<std::string> &spilt)
255 {
256     std::vector<int32_t> array;
257     for (auto iter = spilt.begin(); iter != spilt.end(); iter++) {
258         int32_t num = -1;
259         if (!StrToInt(*iter, num)) {
260             MEDIA_LOGE("call StrToInt func false, input str is: %{public}s", iter->c_str());
261             return array;
262         }
263         array.push_back(num);
264     }
265     return array;
266 }
267 
TransMapAsIntegerArray(const std::unordered_map<std::string,int> & capabilityMap,const std::vector<std::string> & spilt)268 std::vector<int32_t> AVCodecXmlParser::TransMapAsIntegerArray(
269     const std::unordered_map<std::string, int> &capabilityMap,
270     const std::vector<std::string> &spilt)
271 {
272     std::vector<int32_t> res;
273     for (auto iter = spilt.begin(); iter != spilt.end(); iter++) {
274         if (capabilityMap.find(*iter) != capabilityMap.end()) {
275             res.emplace_back(capabilityMap.at(*iter));
276         } else {
277             MEDIA_LOGD("can not find %{public}s in capabilityMap", iter->c_str());
278         }
279     }
280     return res;
281 }
282 
SpiltKeyList(const std::string & str,const std::string & delim,std::vector<std::string> & spilt)283 bool AVCodecXmlParser::SpiltKeyList(const std::string &str, const std::string &delim,
284     std::vector<std::string> &spilt)
285 {
286     if (str == "") {
287         return false;
288     }
289     std::string strAddDelim = str;
290     if (str.back() != delim.back()) {
291         strAddDelim = str + delim;
292     }
293     size_t size = strAddDelim.size();
294     for (size_t i = 0; i < size; ++i) {
295         size_t pos = strAddDelim.find(delim, i);
296         if (pos != strAddDelim.npos) {
297             std::string s = strAddDelim.substr(i, pos - i);
298             spilt.push_back(s);
299             i = pos + delim.size() - 1;
300         }
301     }
302     return true;
303 }
304 
SetCapabilityStringData(std::unordered_map<std::string,std::string &> dataMap,const std::string & capabilityKey,const std::string & capabilityValue)305 bool AVCodecXmlParser::SetCapabilityStringData(std::unordered_map<std::string, std::string&> dataMap,
306     const std::string &capabilityKey, const std::string &capabilityValue)
307 {
308     dataMap.at(capabilityKey) = capabilityValue;
309     return true;
310 }
311 
SetCapabilityIntData(std::unordered_map<std::string,int32_t &> dataMap,const std::string & capabilityKey,const std::string & capabilityValue)312 bool AVCodecXmlParser::SetCapabilityIntData(std::unordered_map<std::string, int32_t&> dataMap,
313     const std::string &capabilityKey, const std::string &capabilityValue)
314 {
315     if (CODEC_TYPE_MAP.find(capabilityValue) != CODEC_TYPE_MAP.end()) {
316         dataMap.at(capabilityKey) = CODEC_TYPE_MAP.at(capabilityValue);
317     } else {
318         MEDIA_LOGD("The value of %{public}s in the configuration file is incorrect.", capabilityValue.c_str());
319         return false;
320     }
321     return true;
322 }
323 
SetCapabilityBoolData(std::unordered_map<std::string,bool &> dataMap,const std::string & capabilityKey,const std::string & capabilityValue)324 bool AVCodecXmlParser::SetCapabilityBoolData(std::unordered_map<std::string, bool&> dataMap,
325     const std::string &capabilityKey, const std::string &capabilityValue)
326 {
327     if (capabilityValue == "true") {
328         dataMap.at(capabilityKey) = true;
329     } else if (capabilityValue == "false") {
330         dataMap.at(capabilityKey) = false;
331     } else {
332         MEDIA_LOGD("The value of %{public}s in the configuration file is incorrect.", capabilityValue.c_str());
333         return false;
334     }
335     return true;
336 }
337 
SetCapabilityRangeData(std::unordered_map<std::string,Range &> dataMap,const std::string & capabilityKey,const std::string & capabilityValue)338 bool AVCodecXmlParser::SetCapabilityRangeData(std::unordered_map<std::string, Range&> dataMap,
339     const std::string &capabilityKey, const std::string &capabilityValue)
340 {
341     Range range;
342     bool ret = TransStrAsRange(capabilityValue, range);
343     CHECK_AND_RETURN_RET_LOG(ret != false, false, "failed:can not trans %{public}s", capabilityValue.c_str());
344     dataMap.at(capabilityKey) = range;
345     return true;
346 }
347 
SetCapabilitySizeData(std::unordered_map<std::string,ImgSize &> dataMap,const std::string & capabilityKey,const std::string & capabilityValue)348 bool AVCodecXmlParser::SetCapabilitySizeData(std::unordered_map<std::string, ImgSize&> dataMap,
349     const std::string &capabilityKey, const std::string &capabilityValue)
350 {
351     ImgSize size;
352     bool ret = TransStrAsSize(capabilityValue, size);
353     CHECK_AND_RETURN_RET_LOG(ret != false, false, "failed:can not trans %{public}s", capabilityValue.c_str());
354     dataMap.at(capabilityKey) = size;
355     return true;
356 }
357 
SetCapabilityHashRangeData(std::unordered_map<std::string,std::map<ImgSize,Range> &> dataMap,const std::string & capabilityKey,const std::string & capabilityValue)358 bool AVCodecXmlParser::SetCapabilityHashRangeData(std::unordered_map<std::string, std::map<ImgSize, Range>&> dataMap,
359     const std::string &capabilityKey, const std::string &capabilityValue)
360 {
361     std::map<ImgSize, Range> resolutionFrameRateMap;
362     std::vector<std::string> spilt;
363     bool ret = SpiltKeyList(capabilityValue, ",", spilt);
364     CHECK_AND_RETURN_RET_LOG(ret != false, false, "failed:can not split %{public}s", capabilityValue.c_str());
365     for (auto iter = spilt.begin(); iter != spilt.end(); iter++) {
366         std::vector<std::string> resolutionFrameRateVector;
367         ImgSize resolution;
368         Range frameRate;
369         ret = SpiltKeyList(*iter, "@", resolutionFrameRateVector);
370         CHECK_AND_RETURN_RET_LOG(ret != false && resolutionFrameRateVector.size() == PAIR_LENGTH, false,
371             "failed:can not trans %{public}s", iter->c_str());
372         if (!(TransStrAsSize(resolutionFrameRateVector[0], resolution) &&
373               TransStrAsRange(resolutionFrameRateVector[1], frameRate))) {
374             MEDIA_LOGD("failed:can not trans %{public}s for resolution or frame rate", iter->c_str());
375             return false;
376         }
377         resolutionFrameRateMap.insert(std::make_pair(resolution, frameRate));
378     }
379     dataMap.at(capabilityKey) = resolutionFrameRateMap;
380     return true;
381 }
382 
IsNumberArray(const std::vector<std::string> & strArray)383 bool AVCodecXmlParser::IsNumberArray(const std::vector<std::string> &strArray)
384 {
385     for (auto iter = strArray.begin(); iter != strArray.end(); iter++) {
386         for (char const &c : *iter) {
387             if (std::isdigit(c) == 0) {
388                 return false;
389             }
390         }
391     }
392     return true;
393 }
394 
SetCapabilityVectorData(std::unordered_map<std::string,std::vector<int32_t> &> dataMap,const std::string & capabilityKey,const std::string & capabilityValue)395 bool AVCodecXmlParser::SetCapabilityVectorData(std::unordered_map<std::string, std::vector<int32_t>&> dataMap,
396     const std::string &capabilityKey, const std::string &capabilityValue)
397 {
398     std::vector<std::string> spilt;
399     std::vector<int32_t> array;
400     bool ret = SpiltKeyList(capabilityValue, ",", spilt);
401     CHECK_AND_RETURN_RET_LOG(ret != false, false, "failed:can not split %{public}s", capabilityValue.c_str());
402     if (spilt.size() > 0) {
403         std::string probe = spilt[0];
404         if (VIDEO_PROFILE_MAP.find(probe) != VIDEO_PROFILE_MAP.end()) {
405             array = TransMapAsIntegerArray(VIDEO_PROFILE_MAP, spilt);
406         } else if (AUDIO_PROFILE_MAP.find(probe) != AUDIO_PROFILE_MAP.end()) {
407             array = TransMapAsIntegerArray(AUDIO_PROFILE_MAP, spilt);
408         } else if (VIDEO_FORMAT_MAP.find(probe) != VIDEO_FORMAT_MAP.end()) {
409             array = TransMapAsIntegerArray(VIDEO_FORMAT_MAP, spilt);
410         } else if (AUDIO_FORMAT_MAP.find(probe) != AUDIO_FORMAT_MAP.end()) {
411             array = TransMapAsIntegerArray(AUDIO_FORMAT_MAP, spilt);
412         } else if (BITRATE_MODE_MAP.find(probe) != BITRATE_MODE_MAP.end()) {
413             array = TransMapAsIntegerArray(BITRATE_MODE_MAP, spilt);
414         } else if (IsNumberArray(spilt)) {
415             array = TransStrAsIntegerArray(spilt);
416         } else {
417             MEDIA_LOGD("The value of %{public}s in the configuration file is incorrect.", capabilityValue.c_str());
418             return false;
419         }
420         dataMap.at(capabilityKey) = array;
421     }
422     return true;
423 }
424 
SetCapabilityData(CapabilityData & data,const std::string & capabilityKey,const std::string & capabilityValue) const425 bool AVCodecXmlParser::SetCapabilityData(CapabilityData &data, const std::string &capabilityKey,
426                                          const std::string &capabilityValue) const
427 {
428     std::unordered_map<std::string, std::string&> capabilityStringMap = {
429         {"codecName", data.codecName}, {"mimeType", data.mimeType}};
430 
431     std::unordered_map<std::string, int32_t&> capabilityIntMap = {{"codecType", data.codecType}};
432 
433     std::unordered_map<std::string, bool&> capabilityBoolMap = {{"isVendor", data.isVendor}};
434 
435     std::unordered_map<std::string, ImgSize&> capabilitySizeMap = {{"blockSize", data.blockSize}};
436 
437     std::unordered_map<std::string, std::map<ImgSize, Range>&> capabilityHashRangeMap = {
438         {"measuredFrameRate", data.measuredFrameRate}};
439 
440     std::unordered_map<std::string, Range&> capabilityRangeMap = {
441         {"bitrate", data.bitrate}, {"channels", data.channels}, {"complexity", data.complexity},
442         {"alignment", data.alignment}, {"width", data.width}, {"height", data.height}, {"frameRate", data.frameRate},
443         {"encodeQuality", data.encodeQuality}, {"quality", data.quality}, {"blockPerFrame", data.blockPerFrame},
444         {"blockPerSecond", data.blockPerSecond}};
445 
446     std::unordered_map<std::string, std::vector<int32_t>&> capabilityVectorMap = {
447         {"sampleRate", data.sampleRate}, {"format", data.format}, {"profiles", data.profiles},
448         {"bitrateMode", data.bitrateMode}, {"levels", data.levels}};
449 
450     bool ret = false;
451     if (capabilityStringMap.find(capabilityKey) != capabilityStringMap.end()) {
452         ret = SetCapabilityStringData(capabilityStringMap, capabilityKey, capabilityValue);
453         CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilityStringData failed");
454     } else if (capabilityIntMap.find(capabilityKey) != capabilityIntMap.end()) {
455         ret = SetCapabilityIntData(capabilityIntMap, capabilityKey, capabilityValue);
456         CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilityIntData failed");
457     } else if (capabilityBoolMap.find(capabilityKey) != capabilityBoolMap.end()) {
458         ret = SetCapabilityBoolData(capabilityBoolMap, capabilityKey, capabilityValue);
459         CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilityBoolData failed");
460     } else if (capabilitySizeMap.find(capabilityKey) != capabilitySizeMap.end()) {
461         ret = SetCapabilitySizeData(capabilitySizeMap, capabilityKey, capabilityValue);
462         CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilitySizeData failed");
463     } else if (capabilityHashRangeMap.find(capabilityKey) != capabilityHashRangeMap.end()) {
464         ret = SetCapabilityHashRangeData(capabilityHashRangeMap, capabilityKey, capabilityValue);
465         CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilityHashRangeData failed");
466     } else if (capabilityRangeMap.find(capabilityKey) != capabilityRangeMap.end()) {
467         ret = SetCapabilityRangeData(capabilityRangeMap, capabilityKey, capabilityValue);
468         CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilityRangeData failed");
469     } else if (capabilityVectorMap.find(capabilityKey) != capabilityVectorMap.end()) {
470         ret = SetCapabilityVectorData(capabilityVectorMap, capabilityKey, capabilityValue);
471         CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilityVectorData failed");
472     } else {
473         CHECK_AND_RETURN_RET_LOG(ret != false, false, "can not find capabilityKey: %{public}s", capabilityKey.c_str());
474     }
475     return true;
476 }
477 
ParseData(xmlNode * node)478 bool AVCodecXmlParser::ParseData(xmlNode *node)
479 {
480     xmlNode *child = node->xmlChildrenNode;
481     std::string capabilityValue;
482     CapabilityData capabilityData;
483     for (; child != nullptr; child = child->next) {
484         if (!xmlStrEqual(child->name, reinterpret_cast<const xmlChar*>("Item"))) {
485             continue;
486         }
487         for (auto it = capabilityKeys_.begin(); it != capabilityKeys_.end(); it++) {
488             std::string capabilityKey = *it;
489             if (xmlHasProp(child, reinterpret_cast<xmlChar*>(const_cast<char*>(capabilityKey.c_str())))) {
490                 xmlChar *pXmlProp = xmlGetProp(
491                     child, reinterpret_cast<xmlChar*>(const_cast<char*>(capabilityKey.c_str())));
492                 CHECK_AND_CONTINUE(pXmlProp != nullptr);
493                 capabilityValue = std::string(reinterpret_cast<char*>(pXmlProp));
494                 bool ret = SetCapabilityData(capabilityData, capabilityKey, capabilityValue);
495                 CHECK_AND_RETURN_RET_LOG(ret != false, false, "SetCapabilityData failed");
496                 break;
497             }
498         }
499     }
500     capabilityDataArray_.push_back(capabilityData);
501     return true;
502 }
503 
GetNodeNameAsInt(xmlNode * node)504 NodeName AVCodecXmlParser::GetNodeNameAsInt(xmlNode *node)
505 {
506     if (xmlStrEqual(node->name, reinterpret_cast<const xmlChar*>("Codecs"))) {
507         return CODECS;
508     } else if (xmlStrEqual(node->name, reinterpret_cast<const xmlChar*>("AudioCodecs"))) {
509         return AUDIO_CODECS;
510     } else if (xmlStrEqual(node->name, reinterpret_cast<const xmlChar*>("VideoCodecs"))) {
511         return VIDEO_CODECS;
512     } else if (xmlStrEqual(node->name, reinterpret_cast<const xmlChar*>("AudioDecoder"))) {
513         return AUDIO_DECODER;
514     } else if (xmlStrEqual(node->name, reinterpret_cast<const xmlChar*>("AudioEncoder"))) {
515         return AUDIO_ENCODER;
516     } else if (xmlStrEqual(node->name, reinterpret_cast<const xmlChar*>("VideoDecoder"))) {
517         return VIDEO_DECODER;
518     } else if (xmlStrEqual(node->name, reinterpret_cast<const xmlChar*>("VideoEncoder"))) {
519         return VIDEO_ENCODER;
520     } else {
521         return UNKNOWN;
522     }
523 }
524 
GetCapabilityDataArray() const525 std::vector<CapabilityData> AVCodecXmlParser::GetCapabilityDataArray() const
526 {
527     return capabilityDataArray_;
528 }
529 } // namespace Media
530 } // namespace OHOS