1 /* 2 // Copyright(c)2014 IntelCorporation 3 // 4 // LicensedundertheApacheLicense,Version2.0(the"License"); 5 // youmaynotusethisfileexceptincompliancewiththeLicense. 6 // YoumayobtainacopyoftheLicenseat 7 // 8 // http://www.apache.org/licenses/LICENSE-2.0 9 // 10 // Unlessrequiredbyapplicablelaworagreedtoinwriting,software 11 // distributedundertheLicenseisdistributedonan"ASIS"BASIS, 12 // WITHOUTWARRANTIESORCONDITIONSOFANYKIND,eitherexpressorimplied. 13 // SeetheLicenseforthespecificlanguagegoverningpermissionsand 14 // limitationsundertheLicense. 15 */ 16 17 #include <common/utils/HwcTrace.h> 18 #include <Hwcomposer.h> 19 #include <BufferManager.h> 20 #include <ips/anniedale/AnnCursorPlane.h> 21 #include <ips/tangier/TngGrallocBuffer.h> 22 #include <hal_public.h> 23 24 namespace android { 25 namespace intel { 26 27 AnnCursorPlane::AnnCursorPlane(int index, int disp) 28 : DisplayPlane(index, PLANE_CURSOR, disp) 29 { 30 CTRACE(); 31 memset(&mContext, 0, sizeof(mContext)); 32 memset(&mCrop, 0, sizeof(mCrop)); 33 } 34 35 AnnCursorPlane::~AnnCursorPlane() 36 { 37 CTRACE(); 38 } 39 40 bool AnnCursorPlane::enable() 41 { 42 return enablePlane(true); 43 } 44 45 bool AnnCursorPlane::disable() 46 { 47 return enablePlane(false); 48 } 49 50 bool AnnCursorPlane::reset() 51 { 52 // clear mCrop once reset 53 memset(&mCrop, 0, sizeof(mCrop)); 54 return true; 55 } 56 57 void* AnnCursorPlane::getContext() const 58 { 59 CTRACE(); 60 return (void *)&mContext; 61 } 62 63 void AnnCursorPlane::setZOrderConfig(ZOrderConfig& config, void *nativeConfig) 64 { 65 (void) config; 66 (void) nativeConfig; 67 68 CTRACE(); 69 } 70 71 bool AnnCursorPlane::setDataBuffer(uint32_t handle) 72 { 73 bool ret; 74 75 if (!handle) { 76 ELOGTRACE("handle is NULL"); 77 return false; 78 } 79 80 ret = DisplayPlane::setDataBuffer(handle); 81 if (ret == false) { 82 ELOGTRACE("failed to set data buffer"); 83 return ret; 84 } 85 86 return true; 87 } 88 89 bool AnnCursorPlane::setDataBuffer(BufferMapper& mapper) 90 { 91 int w = mapper.getWidth(); 92 int h = mapper.getHeight(); 93 int cursorSize = 0; 94 95 CTRACE(); 96 97 // setup plane position 98 int dstX = mPosition.x; 99 int dstY = mPosition.y; 100 int dstW = mPosition.w; 101 int dstH = mPosition.h; 102 103 if (h < w) { 104 cursorSize = h; 105 } else { 106 cursorSize = w; 107 } 108 109 uint32_t cntr = 0; 110 if (64 <= cursorSize && cursorSize < 128) { 111 cursorSize = 64; 112 cntr = 0x7; 113 } else if (128 <= cursorSize && cursorSize < 256) { 114 cursorSize = 128; 115 cntr = 0x2; 116 } else { 117 cursorSize = 256; 118 cntr = 0x3; 119 } 120 121 if (mapper.getFormat() == HAL_PIXEL_FORMAT_RGBA_8888) { 122 cntr |= 1 << 5; 123 } else if (mapper.getFormat() == HAL_PIXEL_FORMAT_BGRA_8888) { 124 // swap color from BGRA to RGBA - alpha is MSB 125 uint8_t *p = (uint8_t *)(mapper.getCpuAddress(0)); 126 uint8_t *srcPixel; 127 uint32_t stride = mapper.getStride().rgb.stride; 128 uint8_t temp; 129 if (!p) { 130 return false; 131 } 132 133 for (int i = 0; i < cursorSize; i++) { 134 for (int j = 0; j < cursorSize; j++) { 135 srcPixel = p + i*stride + j*4; 136 temp = srcPixel[0]; 137 srcPixel[0] = srcPixel[2]; 138 srcPixel[2] = temp; 139 } 140 } 141 cntr |= 1 << 5; 142 } else { 143 ELOGTRACE("invalid color format"); 144 return false; 145 } 146 147 // TODO: clean spare mem to be 0 in gralloc instead 148 uint8_t *p = (uint8_t *)(mapper.getCpuAddress(0)); 149 uint8_t *srcPixel; 150 uint32_t stride = mapper.getStride().rgb.stride; 151 uint8_t temp; 152 if (!p) { 153 return false; 154 } 155 156 if (mCrop.w == 0 && mCrop.h == 0) { 157 mCrop = mSrcCrop; 158 for (int i = 0; i < cursorSize; i++) { 159 for (int j = 0; j < cursorSize; j++) { 160 srcPixel = p + i*stride + j*4; 161 temp = srcPixel[0]; 162 if (i >= mCrop.h || j >= mCrop.w) { 163 if (srcPixel[0] == 0 && 164 srcPixel[3] == 0xff) 165 srcPixel[3] = 0; 166 } 167 } 168 } 169 } 170 171 // update context 172 mContext.type = DC_CURSOR_PLANE; 173 mContext.ctx.cs_ctx.index = mIndex; 174 mContext.ctx.cs_ctx.pipe = mDevice; 175 mContext.ctx.cs_ctx.cntr = cntr; 176 mContext.ctx.cs_ctx.surf = mapper.getGttOffsetInPage(0) << 12; 177 178 mContext.ctx.cs_ctx.pos = 0; 179 if (dstX < 0) { 180 mContext.ctx.cs_ctx.pos |= 1 << 15; 181 dstX = -dstX; 182 } 183 if (dstY < 0) { 184 mContext.ctx.cs_ctx.pos |= 1 << 31; 185 dstY = -dstY; 186 } 187 mContext.ctx.cs_ctx.pos |= (dstY & 0xfff) << 16 | (dstX & 0xfff); 188 return true; 189 } 190 191 bool AnnCursorPlane::enablePlane(bool enabled) 192 { 193 RETURN_FALSE_IF_NOT_INIT(); 194 195 struct drm_psb_register_rw_arg arg; 196 memset(&arg, 0, sizeof(struct drm_psb_register_rw_arg)); 197 if (enabled) { 198 arg.plane_enable_mask = 1; 199 } else { 200 arg.plane_disable_mask = 1; 201 } 202 203 arg.plane.type = DC_CURSOR_PLANE; 204 arg.plane.index = mIndex; 205 arg.plane.ctx = 0; 206 207 // issue ioctl 208 Drm *drm = Hwcomposer::getInstance().getDrm(); 209 bool ret = drm->writeReadIoctl(DRM_PSB_REGISTER_RW, &arg, sizeof(arg)); 210 if (ret == false) { 211 WLOGTRACE("plane enabling (%d) failed with error code %d", enabled, ret); 212 return false; 213 } 214 215 return true; 216 } 217 218 bool AnnCursorPlane::isDisabled() 219 { 220 RETURN_FALSE_IF_NOT_INIT(); 221 222 struct drm_psb_register_rw_arg arg; 223 memset(&arg, 0, sizeof(struct drm_psb_register_rw_arg)); 224 225 arg.plane.type = DC_CURSOR_PLANE; 226 arg.get_plane_state_mask = 1; 227 arg.plane.index = mIndex; 228 arg.plane.ctx = 0; 229 230 // issue ioctl 231 Drm *drm = Hwcomposer::getInstance().getDrm(); 232 bool ret = drm->writeReadIoctl(DRM_PSB_REGISTER_RW, &arg, sizeof(arg)); 233 if (ret == false) { 234 WLOGTRACE("plane state query failed with error code %d", ret); 235 return false; 236 } 237 238 return arg.plane.ctx == PSB_DC_PLANE_DISABLED; 239 } 240 241 void AnnCursorPlane::postFlip() 242 { 243 // prevent mUpdateMasks from being reset 244 // skipping flip may cause flicking 245 } 246 247 } // namespace intel 248 } // namespace android 249