• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2021 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 #include "DisplayConfig.h"
18 
19 #include <unordered_map>
20 
21 namespace {
22 
23 template <class T>
hashCombine(size_t & hash,const T & value)24 inline void hashCombine(size_t& hash, const T& value) {
25   std::hash<T> hasher;
26   hash ^= hasher(value) + 0x9e3779b9 + (hash << 6) + (hash >> 2);
27 }
28 
29 }  // namespace
30 
setAttribute(HWC2::Attribute attribute,int32_t value)31 void DisplayConfig::setAttribute(HWC2::Attribute attribute, int32_t value) {
32   if (attribute == HWC2::Attribute::Width) {
33     mWidth = value;
34   }
35   if (attribute == HWC2::Attribute::Height) {
36     mHeight = value;
37   }
38   if (attribute == HWC2::Attribute::DpiX) {
39     mDpiX = value;
40   }
41   if (attribute == HWC2::Attribute::DpiY) {
42     mDpiY = value;
43   }
44   if (attribute == HWC2::Attribute::VsyncPeriod) {
45     mVsyncPeriodNanos = value;
46   }
47   if (attribute == HWC2::Attribute::ConfigGroup) {
48     mConfigGroup = value;
49   }
50 }
51 
getAttribute(HWC2::Attribute attribute) const52 int32_t DisplayConfig::getAttribute(HWC2::Attribute attribute) const {
53   if (attribute == HWC2::Attribute::Width) {
54     return mWidth;
55   }
56   if (attribute == HWC2::Attribute::Height) {
57     return mHeight;
58   }
59   if (attribute == HWC2::Attribute::DpiX) {
60     // From hwcomposer2.h, HWC2_ATTRIBUTE_DPI_X returns "Dots per thousand
61     // inches (DPI * 1000)".
62     return getDotsPerThousandInchesX();
63   }
64   if (attribute == HWC2::Attribute::DpiY) {
65     // From hwcomposer2.h, HWC2_ATTRIBUTE_DPI_Y returns "Dots per thousand
66     // inches (DPI * 1000)"
67     return getDotsPerThousandInchesY();
68   }
69   if (attribute == HWC2::Attribute::VsyncPeriod) {
70     return mVsyncPeriodNanos;
71   }
72   if (attribute == HWC2::Attribute::ConfigGroup) {
73     return mConfigGroup;
74   }
75   return -1;
76 }
77 
toString() const78 std::string DisplayConfig::toString() const {
79   std::string output;
80   output += " w:" + std::to_string(mWidth);
81   output += " h:" + std::to_string(mHeight);
82   output += " dpi-x:" + std::to_string(mDpiX);
83   output += " dpi-y:" + std::to_string(mDpiY);
84   output += " vsync:" + std::to_string(1e9 / mVsyncPeriodNanos);
85   output += " config-group:" + std::to_string(mConfigGroup);
86   return output;
87 }
88 
89 /*static*/
addConfigGroups(std::vector<DisplayConfig> * configs)90 void DisplayConfig::addConfigGroups(std::vector<DisplayConfig>* configs) {
91   // From /hardware/interfaces/graphics/composer/2.4/IComposerClient.hal:
92   // "Configurations which share the same config group are similar in all
93   // attributes except for the vsync period."
94   struct ConfigForGroupHash {
95     size_t operator()(const DisplayConfig& config) const {
96       size_t hash = 0;
97       hashCombine(hash, config.mWidth);
98       hashCombine(hash, config.mHeight);
99       hashCombine(hash, config.mDpiX);
100       hashCombine(hash, config.mDpiY);
101       return hash;
102     }
103   };
104   struct ConfigForGroupEq {
105     size_t operator()(const DisplayConfig& a, const DisplayConfig& b) const {
106       if (a.mWidth != b.mWidth) {
107         return a.mWidth < b.mWidth;
108       }
109       if (a.mHeight != b.mHeight) {
110         return a.mHeight < b.mHeight;
111       }
112       if (a.mDpiX != b.mDpiX) {
113         return a.mDpiX < b.mDpiX;
114       }
115       return a.mDpiY < b.mDpiY;
116     }
117   };
118 
119   std::unordered_map<DisplayConfig, int32_t, ConfigForGroupHash,
120                      ConfigForGroupEq>
121       configToConfigGroup;
122 
123   for (auto& config : *configs) {
124     auto [it, inserted] =
125         configToConfigGroup.try_emplace(config, configToConfigGroup.size());
126     config.setConfigGroup(it->second);
127   }
128 }