• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2023 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 <algorithm>
16 #include <chrono>
17 #include <regex>
18 #include "rs_round_corner_config.h"
19 
20 using std::chrono::high_resolution_clock;
21 using std::chrono::microseconds;
22 
23 namespace OHOS {
24 namespace Rosen {
25 namespace rs_rcd {
26 const char REG_NUM[] = "^[+-]?([0-9]+([.][0-9]*)?|[.][0-9]+)$"; // regular expression of check number
27 
RegexMatch(const std::string & str,const std::string & pattern)28 bool XMLReader::RegexMatch(const std::string& str, const std::string& pattern)
29 {
30     std::smatch result;
31     std::regex r(pattern);
32     return std::regex_match(str, result, r);
33 }
34 
RegexMatchNum(std::string & str)35 bool XMLReader::RegexMatchNum(std::string& str)
36 {
37     // remove space from string before match
38     str.erase(remove(str.begin(), str.end(), ' '), str.end());
39     return RegexMatch(str, std::string(REG_NUM));
40 }
41 
FindNode(const xmlNodePtr & src,const std::string & index)42 xmlNodePtr XMLReader::FindNode(const xmlNodePtr& src, const std::string& index)
43 {
44     xmlNodePtr startPtr = src->children;
45     while (startPtr != nullptr) {
46         auto name = startPtr->name;
47         if (xmlStrEqual(name, BAD_CAST(index.c_str())) == 1) {
48             return startPtr;
49         }
50         startPtr = startPtr->next;
51     }
52     RS_LOGD("[%{public}s] can not found node %{public}s! \n", __func__, index.c_str());
53     return nullptr;
54 }
55 
ReadAttrStr(const xmlNodePtr & src,const std::string & attr)56 std::string XMLReader::ReadAttrStr(const xmlNodePtr& src, const std::string& attr)
57 {
58     auto result = reinterpret_cast<char*>((xmlGetProp(src, BAD_CAST(attr.c_str()))));
59     if (result == nullptr) {
60         RS_LOGE("[%{public}s] can not found attribute %{public}s! \n", __func__, attr.c_str());
61         return std::string("");
62     }
63     std::string str(result);
64     xmlFree(result);
65     return str;
66 }
67 
ReadAttrInt(const xmlNodePtr & src,const std::string & attr)68 int XMLReader::ReadAttrInt(const xmlNodePtr& src, const std::string& attr)
69 {
70     auto result = reinterpret_cast<char*>((xmlGetProp(src, BAD_CAST(attr.c_str()))));
71     if (result == nullptr) {
72         RS_LOGE("[%{public}s] can not found attribute %{public}s! \n", __func__, attr.c_str());
73         return 0;
74     }
75     std::string num(result);
76     xmlFree(result);
77     if (RegexMatchNum(num)) {
78         return std::atoi(num.c_str());
79     }
80     RS_LOGE("[%{public}s] attribute %{public}s can not convert to int! \n", __func__, attr.c_str());
81     return 0;
82 }
83 
ReadAttrFloat(const xmlNodePtr & src,const std::string & attr)84 float XMLReader::ReadAttrFloat(const xmlNodePtr& src, const std::string& attr)
85 {
86     auto result = reinterpret_cast<char*>((xmlGetProp(src, BAD_CAST(attr.c_str()))));
87     if (result == nullptr) {
88         RS_LOGE("[%{public}s] can not found attribute %{public}s! \n", __func__, attr.c_str());
89         return 0.0f;
90     }
91     std::string num(result);
92     xmlFree(result);
93     if (RegexMatchNum(num)) {
94         return std::atof(num.c_str());
95     }
96     RS_LOGE("[%{public}s] attribute %{public}s can not convert to float! \n", __func__, attr.c_str());
97     return 0;
98 }
99 
ReadAttrBool(const xmlNodePtr & src,const std::string & attr)100 bool XMLReader::ReadAttrBool(const xmlNodePtr& src, const std::string& attr)
101 {
102     auto result = reinterpret_cast<char*>((xmlGetProp(src, BAD_CAST(attr.c_str()))));
103     if (result == nullptr) {
104         RS_LOGE("[%{public}s] can not found attribute %{public}s! \n", __func__, attr.c_str());
105         return false;
106     }
107     auto istrue = strcmp(result, "true") == 0 ? true : false;
108     xmlFree(result);
109     return istrue;
110 }
111 
ReadXmlNode(const xmlNodePtr & ptr,const std::string & supportAttr,const std::string & modeAttr)112 bool SupportConfig::ReadXmlNode(const xmlNodePtr& ptr, const std::string& supportAttr, const std::string& modeAttr)
113 {
114     auto a1 = xmlGetProp(ptr, BAD_CAST(supportAttr.c_str()));
115     if (a1 == nullptr) {
116         RS_LOGE("[%{public}s] can not found supportAttr %{public}s! \n", __func__, supportAttr.c_str());
117         return false;
118     }
119     support = XMLReader::ReadAttrBool(ptr, supportAttr);
120     mode = XMLReader::ReadAttrInt(ptr, modeAttr);
121     xmlFree(a1);
122     return true;
123 }
124 
ReadXmlNode(const xmlNodePtr & ptr,const std::vector<std::string> & attrArray)125 bool RoundCornerLayer::ReadXmlNode(const xmlNodePtr& ptr, const std::vector<std::string>& attrArray)
126 {
127     const int layerAttrSize = 7;
128     if (attrArray.size() < layerAttrSize || ptr == nullptr) {
129         RS_LOGE("[%{public}s] attribute size less than 7! \n", __func__);
130         return false;
131     }
132     const int fileIndex = 0;
133     const int offsetXIndex = 1;
134     const int offsetYIndex = 2;
135     const int binFileIndex = 3;
136     const int bufferSizeIndex = 4;
137     const int cldWidthIndex = 5;
138     const int cldHeightIndex = 6;
139     fileName = XMLReader::ReadAttrStr(ptr, attrArray[fileIndex]);
140     offsetX = XMLReader::ReadAttrInt(ptr, attrArray[offsetXIndex]);
141     offsetY = XMLReader::ReadAttrInt(ptr, attrArray[offsetYIndex]);
142     binFileName = XMLReader::ReadAttrStr(ptr, attrArray[binFileIndex]);
143     bufferSize = XMLReader::ReadAttrInt(ptr, attrArray[bufferSizeIndex]);
144     cldWidth = XMLReader::ReadAttrInt(ptr, attrArray[cldWidthIndex]);
145     cldHeight = XMLReader::ReadAttrInt(ptr, attrArray[cldHeightIndex]);
146     return true;
147 }
148 
ReadXmlNode(const xmlNodePtr & portraitNodePtr)149 bool RogPortrait::ReadXmlNode(const xmlNodePtr& portraitNodePtr)
150 {
151     if (portraitNodePtr == nullptr) {
152         RS_LOGE("[%{public}s] input node is null! \n", __func__);
153         return false;
154     }
155     std::vector<std::string> attrList = { ATTR_FILENAME, ATTR_OFFSET_X, ATTR_OFFSET_Y,
156         ATTR_BINFILENAME, ATTR_BUFFERSIZE, ATTR_CLDWIDTH, ATTR_CLDHEIGHT };
157 
158     auto layerUpPtr = XMLReader::FindNode(portraitNodePtr, std::string(NODE_LAYERUP));
159     if (layerUpPtr == nullptr) {
160         RS_LOGE("[%{public}s] layerUpPtr node is null! \n", __func__);
161         return false;
162     }
163     layerUp.ReadXmlNode(layerUpPtr, attrList);
164 
165     auto layerDownPtr = XMLReader::FindNode(portraitNodePtr, std::string(NODE_LAYERDOWN));
166     if (layerDownPtr == nullptr) {
167         RS_LOGE("[%{public}s] layerDownPtr node is null! \n", __func__);
168         return false;
169     }
170     layerDown.ReadXmlNode(layerDownPtr, attrList);
171 
172     auto layerHidePtr = XMLReader::FindNode(portraitNodePtr, std::string(NODE_LAYERHIDE));
173     if (layerHidePtr == nullptr) {
174         RS_LOGE("[%{public}s] layerHidePtr node is null! \n", __func__);
175         return false;
176     }
177     layerHide.ReadXmlNode(layerHidePtr, attrList);
178     return true;
179 }
180 
ReadXmlNode(const xmlNodePtr & landNodePtr)181 bool RogLandscape::ReadXmlNode(const xmlNodePtr& landNodePtr)
182 {
183     if (landNodePtr == nullptr) {
184         RS_LOGE("[%{public}s] landNodePtr node is null! \n", __func__);
185         return false;
186     }
187     std::vector<std::string> attrList = { ATTR_FILENAME, ATTR_OFFSET_X, ATTR_OFFSET_Y,
188         ATTR_BINFILENAME, ATTR_BUFFERSIZE, ATTR_CLDWIDTH, ATTR_CLDHEIGHT };
189     auto layerUpPtr = XMLReader::FindNode(landNodePtr, std::string(NODE_LAYERUP));
190     if (layerUpPtr == nullptr) {
191         RS_LOGE("[%{public}s] layerUpPtr node is null! \n", __func__);
192         return false;
193     }
194     layerUp.ReadXmlNode(layerUpPtr, attrList);
195     return true;
196 }
197 
ReadXmlNode(const xmlNodePtr & rogNodePtr)198 bool ROGSetting::ReadXmlNode(const xmlNodePtr& rogNodePtr)
199 {
200     if (rogNodePtr == nullptr) {
201         RS_LOGE("[%{public}s] rogNodePtr node is null! \n", __func__);
202         return false;
203     }
204     width = XMLReader::ReadAttrInt(rogNodePtr, std::string(ATTR_WIDTH));
205     height = XMLReader::ReadAttrInt(rogNodePtr, std::string(ATTR_HEIGHT));
206 
207     auto portPtr = XMLReader::FindNode(rogNodePtr, NODE_PORTRAIT);
208     if (portPtr != nullptr) {
209         RogPortrait p;
210         p.ReadXmlNode(portPtr);
211         portraitMap[NODE_PORTRAIT] = p;
212     }
213 
214     auto portSidePtr = XMLReader::FindNode(rogNodePtr, NODE_PORTRAIT_SIDEREGION);
215     if (portSidePtr != nullptr) {
216         RogPortrait p;
217         p.ReadXmlNode(portSidePtr);
218         portraitMap[NODE_PORTRAIT_SIDEREGION] = p;
219     }
220 
221     auto landPtr = XMLReader::FindNode(rogNodePtr, NODE_LANDSCAPE);
222     if (landPtr != nullptr) {
223         RogLandscape p;
224         p.ReadXmlNode(landPtr);
225         landscapeMap[NODE_LANDSCAPE] = p;
226     }
227 
228     auto landSidePtr = XMLReader::FindNode(rogNodePtr, NODE_LANDSCAPE_SIDEREGION);
229     if (landSidePtr != nullptr) {
230         RogLandscape p;
231         p.ReadXmlNode(landSidePtr);
232         landscapeMap[NODE_LANDSCAPE_SIDEREGION] = p;
233     }
234     return true;
235 }
236 
ReadXmlNode(const xmlNodePtr & surfaceConfigNodePtr)237 bool SurfaceConfig::ReadXmlNode(const xmlNodePtr& surfaceConfigNodePtr)
238 {
239     if (surfaceConfigNodePtr == nullptr) {
240         RS_LOGE("[%{public}s] surfaceConfigNodePtr node is null! \n", __func__);
241         return false;
242     }
243 
244     auto topSurfacePtr = XMLReader::FindNode(surfaceConfigNodePtr, std::string(NODE_TOPSURFACE));
245     if (topSurfacePtr == nullptr) {
246         RS_LOGE("[%{public}s] topSurfacePtr node is null! \n", __func__);
247         return false;
248     }
249     topSurface.ReadXmlNode(topSurfacePtr, std::string(ATTR_SUPPORT), std::string(ATTR_DISPLAYMODE));
250 
251     auto bottomSurfacePtr = XMLReader::FindNode(surfaceConfigNodePtr, std::string(NODE_BOTTOMSURFACE));
252     if (bottomSurfacePtr == nullptr) {
253         RS_LOGE("[%{public}s] bottomSurfacePtr node is null! \n", __func__);
254         return false;
255     }
256     bottomSurface.ReadXmlNode(bottomSurfacePtr, std::string(ATTR_SUPPORT), std::string(ATTR_DISPLAYMODE));
257     return true;
258 }
259 
ReadXmlNode(const xmlNodePtr & sideRegionNodePtr)260 bool SideRegionConfig::ReadXmlNode(const xmlNodePtr& sideRegionNodePtr)
261 {
262     if (sideRegionNodePtr == nullptr) {
263         RS_LOGE("[%{public}s] sideRegionNodePtr node is null! \n", __func__);
264         return false;
265     }
266     auto sideRegionPtr = XMLReader::FindNode(sideRegionNodePtr, std::string(NODE_SIDEREGION));
267     if (sideRegionPtr == nullptr) {
268         RS_LOGE("[%{public}s] sideRegionPtr node is null! \n", __func__);
269         return false;
270     }
271     sideRegion.ReadXmlNode(sideRegionPtr, std::string(ATTR_SUPPORT), std::string(ATTR_DISPLAYMODE));
272     return true;
273 }
274 
ReadXmlNode(const xmlNodePtr & ptr,const std::string & supportAttr)275 bool HardwareComposer::ReadXmlNode(const xmlNodePtr& ptr, const std::string& supportAttr)
276 {
277     auto a1 = xmlGetProp(ptr, BAD_CAST(supportAttr.c_str()));
278     if (a1 == nullptr) {
279         RS_LOGE("[%{public}s] supportAttr node is null! \n", __func__);
280         return false;
281     }
282     support = XMLReader::ReadAttrBool(ptr, supportAttr);
283     xmlFree(a1);
284     return true;
285 }
286 
ReadXmlNode(const xmlNodePtr & hardwareComposerNodeptr)287 bool HardwareComposerConfig::ReadXmlNode(const xmlNodePtr& hardwareComposerNodeptr)
288 {
289     if (hardwareComposerNodeptr == nullptr) {
290         RS_LOGE("[%{public}s] hardwareComposerNodeptr node is null! \n", __func__);
291         return false;
292     }
293     auto hardwareComposerPtr = XMLReader::FindNode(hardwareComposerNodeptr, std::string(NODE_HARDWARECOMPOSER));
294     if (hardwareComposerPtr == nullptr) {
295         RS_LOGE("[%{public}s] hardwareComposerPtr node is null! \n", __func__);
296         return false;
297     }
298     hardwareComposer.ReadXmlNode(hardwareComposerPtr, std::string(ATTR_SUPPORT));
299     return true;
300 }
301 
~LCDModel()302 LCDModel::~LCDModel()
303 {
304     for (auto& rog : rogs) {
305         if (rog != nullptr) {
306             delete rog;
307             rog = nullptr;
308         }
309     }
310 }
311 
ReadXmlNode(const xmlNodePtr & lcdNodePtr)312 bool LCDModel::ReadXmlNode(const xmlNodePtr& lcdNodePtr)
313 {
314     if (lcdNodePtr == nullptr) {
315         RS_LOGE("[%{public}s] input lcdNodePtr node is null! \n", __func__);
316         return false;
317     }
318     name = XMLReader::ReadAttrStr(lcdNodePtr, std::string(ATTR_NAME));
319     auto surfaceConfigPtr = XMLReader::FindNode(lcdNodePtr, std::string(NODE_SURFACECONFIG));
320     if (surfaceConfigPtr == nullptr) {
321         RS_LOGW("no surfaceConfig found \n");
322     }
323     surfaceConfig.ReadXmlNode(surfaceConfigPtr);
324 
325     auto sideRegionConfigPtr = XMLReader::FindNode(lcdNodePtr, std::string(NODE_SIDEREGIONCONFIG));
326     if (sideRegionConfigPtr == nullptr) {
327         RS_LOGW("no sideRegionConfig found \n");
328     }
329     sideRegionConfig.ReadXmlNode(sideRegionConfigPtr);
330 
331     auto hardwareComposerConfigPtr = XMLReader::FindNode(lcdNodePtr, std::string(NODE_HARDWARECOMPOSERCONFIG));
332     if (hardwareComposerConfigPtr == nullptr) {
333         RS_LOGW("no harewareComposer found \n");
334     }
335     hardwareConfig.ReadXmlNode(hardwareComposerConfigPtr);
336 
337     xmlNodePtr startPtr = lcdNodePtr->children;
338     while (startPtr != nullptr) {
339         auto name = startPtr->name;
340         if (xmlStrEqual(name, BAD_CAST(NODE_ROG)) == 1) {
341             ROGSetting *rog = new ROGSetting();
342             if (rog->ReadXmlNode(startPtr)) {
343                 rogs.push_back(rog);
344             } else {
345                 delete rog;
346                 rog = nullptr;
347             }
348         }
349         startPtr = startPtr->next;
350     }
351     return true;
352 }
353 
GetSurfaceConfig() const354 SurfaceConfig LCDModel::GetSurfaceConfig() const
355 {
356     return surfaceConfig;
357 }
358 
GetSideRegionConfig() const359 SideRegionConfig LCDModel::GetSideRegionConfig() const
360 {
361     return sideRegionConfig;
362 }
363 
GetHardwareComposerConfig() const364 HardwareComposerConfig LCDModel::GetHardwareComposerConfig() const
365 {
366     return hardwareConfig;
367 }
368 
GetRog(const int w,const int h) const369 ROGSetting* LCDModel::GetRog(const int w, const int h) const
370 {
371     for (auto rog : rogs) {
372         if (rog == nullptr) {
373             continue;
374         }
375         if (rog->width == w && rog->height == h) {
376             return rog;
377         }
378     }
379     return nullptr;
380 }
381 
PrintLayer(const std::string & name,const rs_rcd::RoundCornerLayer & layer)382 void RCDConfig::PrintLayer(const std::string& name, const rs_rcd::RoundCornerLayer& layer)
383 {
384     RS_LOGD("%{public}s->Filename: %{public}s, Offset: %{public}d, %{public}d \n",
385         name.c_str(), layer.fileName.c_str(), layer.offsetX, layer.offsetY);
386     RS_LOGD("BinFilename: %{public}s, BufferSize: %{public}d, cldSize:%{public}d, %{public}d \n",
387         layer.binFileName.c_str(), layer.bufferSize, layer.cldWidth, layer.cldHeight);
388 }
389 
PrintParseRog(rs_rcd::ROGSetting * rog)390 void RCDConfig::PrintParseRog(rs_rcd::ROGSetting* rog)
391 {
392     if (rog == nullptr) {
393         RS_LOGE("no model input \n");
394         return;
395     }
396     for (auto kv : rog->portraitMap) {
397         auto port = kv.second;
398         RS_LOGD("rog: %{public}d, %{public}d, %{public}s: \n", rog->width, rog->height, kv.first.c_str());
399         PrintLayer(std::string("layerUp  "), port.layerUp);
400         PrintLayer(std::string("layerDown"), port.layerDown);
401         PrintLayer(std::string("layerHide"), port.layerHide);
402     }
403     for (auto kv : rog->landscapeMap) {
404         auto port = kv.second;
405         RS_LOGD("rog: %{public}d, %{public}d, %{public}s: \n", rog->width, rog->height, kv.first.c_str());
406         PrintLayer(std::string("layerUp  "), port.layerUp);
407     }
408 }
409 
Load(const std::string & configFile)410 bool RCDConfig::Load(const std::string& configFile)
411 {
412     auto begin = high_resolution_clock::now();
413     xmlKeepBlanksDefault(0);
414     pDoc = xmlReadFile(configFile.c_str(), "", XML_PARSE_RECOVER);
415     if (pDoc == nullptr) {
416         RS_LOGE("RoundCornerDisplay read xml failed \n");
417         CloseXML();
418         return false;
419     }
420     RS_LOGI("RoundCornerDisplay read xml ok \n");
421     pRoot = xmlDocGetRootElement(pDoc);
422     if (pRoot == nullptr) {
423         RS_LOGE("RoundCornerDisplay get xml root failed \n");
424         CloseXML();
425         return false;
426     }
427     xmlNodePtr startPtr = pRoot->children;
428     while (startPtr != nullptr) {
429         auto name = startPtr->name;
430         if (xmlStrEqual(name, BAD_CAST(NODE_LCDMODEL)) == 1) {
431             LCDModel* lcdModel = new LCDModel();
432             if (lcdModel->ReadXmlNode(startPtr)) {
433                 lcdModels.push_back(lcdModel);
434             } else {
435                 delete lcdModel;
436                 lcdModel = nullptr;
437             }
438         }
439         startPtr = startPtr->next;
440     }
441     CloseXML();
442     auto interval = std::chrono::duration_cast<microseconds>(high_resolution_clock::now() - begin);
443     RS_LOGI("RoundCornerDisplay read xml time cost %{public}lld us \n", interval.count());
444     return true;
445 }
446 
GetLcdModel(const std::string & name) const447 LCDModel* RCDConfig::GetLcdModel(const std::string& name) const
448 {
449     if (name.empty()) {
450         RS_LOGE("[%{public}s] name is null! \n", __func__);
451         return nullptr;
452     }
453     for (auto model : lcdModels) {
454         if (model == nullptr) {
455             continue;
456         }
457         if (model->name.compare(name) == 0) {
458             return model;
459         }
460     }
461     RS_LOGE("[%{public}s] lcd not found in name %{public}s! \n", __func__, name.c_str());
462     return nullptr;
463 }
464 
CloseXML()465 void RCDConfig::CloseXML()
466 {
467     if (pDoc != nullptr) {
468         xmlFreeDoc(pDoc);
469         pDoc = nullptr;
470     }
471     xmlCleanupParser();
472     xmlMemoryDump();
473 }
474 
~RCDConfig()475 RCDConfig::~RCDConfig()
476 {
477     for (auto& modelPtr : lcdModels) {
478         if (modelPtr != nullptr) {
479             delete modelPtr;
480             modelPtr = nullptr;
481         }
482     }
483 }
484 } // namespace rs_rcd
485 } // namespace Rosen
486 } // OHOS