1fb299fa2Sopenharmony_ci/* 2fb299fa2Sopenharmony_ci * Copyright (c) 2022 Huawei Device Co., Ltd. 3fb299fa2Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License"); 4fb299fa2Sopenharmony_ci * you may not use this file except in compliance with the License. 5fb299fa2Sopenharmony_ci * You may obtain a copy of the License at 6fb299fa2Sopenharmony_ci * 7fb299fa2Sopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0 8fb299fa2Sopenharmony_ci * 9fb299fa2Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software 10fb299fa2Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS, 11fb299fa2Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12fb299fa2Sopenharmony_ci * See the License for the specific language governing permissions and 13fb299fa2Sopenharmony_ci * limitations under the License. 14fb299fa2Sopenharmony_ci */ 15fb299fa2Sopenharmony_ci#include "fbdev_driver.h" 16fb299fa2Sopenharmony_ci 17fb299fa2Sopenharmony_ci#include <cstdio> 18fb299fa2Sopenharmony_ci#include <cstdlib> 19fb299fa2Sopenharmony_ci#include <cstring> 20fb299fa2Sopenharmony_ci#include <memory> 21fb299fa2Sopenharmony_ci#include <fcntl.h> 22fb299fa2Sopenharmony_ci#include <sys/ioctl.h> 23fb299fa2Sopenharmony_ci#include <sys/mman.h> 24fb299fa2Sopenharmony_ci#include <sys/types.h> 25fb299fa2Sopenharmony_ci#include <unistd.h> 26fb299fa2Sopenharmony_ci#include "log/log.h" 27fb299fa2Sopenharmony_ci#include "securec.h" 28fb299fa2Sopenharmony_ci#include "ui_rotation.h" 29fb299fa2Sopenharmony_ci#include "updater_ui_const.h" 30fb299fa2Sopenharmony_ci 31fb299fa2Sopenharmony_cinamespace Updater { 32fb299fa2Sopenharmony_ciFbdevDriver::~FbdevDriver() 33fb299fa2Sopenharmony_ci{ 34fb299fa2Sopenharmony_ci ReleaseFb(&buff_); 35fb299fa2Sopenharmony_ci} 36fb299fa2Sopenharmony_ci 37fb299fa2Sopenharmony_civoid FbdevDriver::FBLog() const 38fb299fa2Sopenharmony_ci{ 39fb299fa2Sopenharmony_ci LOG(INFO) << "id=" << finfo_.id; 40fb299fa2Sopenharmony_ci LOG(INFO) << "sem_start=" << finfo_.smem_start; 41fb299fa2Sopenharmony_ci LOG(INFO) << "smem_len=" << finfo_.smem_len; 42fb299fa2Sopenharmony_ci LOG(INFO) << "type=" << finfo_.type; 43fb299fa2Sopenharmony_ci LOG(INFO) << "line_length=" << finfo_.line_length; 44fb299fa2Sopenharmony_ci LOG(INFO) << "mmio_start=" << finfo_.mmio_start; 45fb299fa2Sopenharmony_ci LOG(INFO) << "mmio_len=" << finfo_.mmio_len; 46fb299fa2Sopenharmony_ci LOG(INFO) << "visual=" << finfo_.visual; 47fb299fa2Sopenharmony_ci 48fb299fa2Sopenharmony_ci LOG(INFO) << "The xres=" << vinfo_.xres; 49fb299fa2Sopenharmony_ci LOG(INFO) << "The yres=" << vinfo_.yres; 50fb299fa2Sopenharmony_ci LOG(INFO) << "xres_virtual=" << vinfo_.xres_virtual; 51fb299fa2Sopenharmony_ci LOG(INFO) << "yres_virtual=" << vinfo_.yres_virtual; 52fb299fa2Sopenharmony_ci LOG(INFO) << "xoffset=" << vinfo_.xoffset; 53fb299fa2Sopenharmony_ci LOG(INFO) << "yoffset=" << vinfo_.yoffset; 54fb299fa2Sopenharmony_ci LOG(INFO) << "bits_per_pixel is :" << vinfo_.bits_per_pixel; 55fb299fa2Sopenharmony_ci LOG(INFO) << "red.offset=" << vinfo_.red.offset; 56fb299fa2Sopenharmony_ci LOG(INFO) << "red.length=" << vinfo_.red.length; 57fb299fa2Sopenharmony_ci LOG(INFO) << "red.msb_right=" << vinfo_.red.msb_right; 58fb299fa2Sopenharmony_ci LOG(INFO) << "green.offset=" << vinfo_.green.offset; 59fb299fa2Sopenharmony_ci LOG(INFO) << "green.length=" << vinfo_.green.length; 60fb299fa2Sopenharmony_ci LOG(INFO) << "green.msb_right=" << vinfo_.green.msb_right; 61fb299fa2Sopenharmony_ci LOG(INFO) << "blue.offset=" << vinfo_.blue.offset; 62fb299fa2Sopenharmony_ci LOG(INFO) << "blue.length=" << vinfo_.blue.length; 63fb299fa2Sopenharmony_ci LOG(INFO) << "blue.msb_right=" << vinfo_.blue.msb_right; 64fb299fa2Sopenharmony_ci LOG(INFO) << "transp.offset=" << vinfo_.transp.offset; 65fb299fa2Sopenharmony_ci LOG(INFO) << "transp.length=" << vinfo_.transp.length; 66fb299fa2Sopenharmony_ci LOG(INFO) << "transp.msb_right=" << vinfo_.transp.msb_right; 67fb299fa2Sopenharmony_ci LOG(INFO) << "height=" << vinfo_.height; 68fb299fa2Sopenharmony_ci} 69fb299fa2Sopenharmony_ci 70fb299fa2Sopenharmony_cibool FbdevDriver::Init() 71fb299fa2Sopenharmony_ci{ 72fb299fa2Sopenharmony_ci if (devPath_.empty()) { 73fb299fa2Sopenharmony_ci LOG(ERROR) << "dev path is empty, init failed, check whether SetDevPath correctly called"; 74fb299fa2Sopenharmony_ci return false; 75fb299fa2Sopenharmony_ci } 76fb299fa2Sopenharmony_ci int fd = open(devPath_.c_str(), O_RDWR | O_CLOEXEC); 77fb299fa2Sopenharmony_ci if (fd < 0) { 78fb299fa2Sopenharmony_ci LOG(ERROR) << "cannot open fb0"; 79fb299fa2Sopenharmony_ci return false; 80fb299fa2Sopenharmony_ci } 81fb299fa2Sopenharmony_ci 82fb299fa2Sopenharmony_ci (void)FbPowerContrl(fd, false); 83fb299fa2Sopenharmony_ci (void)FbPowerContrl(fd, true); 84fb299fa2Sopenharmony_ci 85fb299fa2Sopenharmony_ci if (ioctl(fd, FBIOGET_FSCREENINFO, &finfo_) < 0) { 86fb299fa2Sopenharmony_ci LOG(ERROR) << "failed to get fb0 info"; 87fb299fa2Sopenharmony_ci close(fd); 88fb299fa2Sopenharmony_ci return false; 89fb299fa2Sopenharmony_ci } 90fb299fa2Sopenharmony_ci 91fb299fa2Sopenharmony_ci if (ioctl(fd, FBIOGET_VSCREENINFO, &vinfo_) < 0) { 92fb299fa2Sopenharmony_ci LOG(ERROR) << "failed to get fb0 info"; 93fb299fa2Sopenharmony_ci close(fd); 94fb299fa2Sopenharmony_ci return false; 95fb299fa2Sopenharmony_ci } 96fb299fa2Sopenharmony_ci 97fb299fa2Sopenharmony_ci FBLog(); 98fb299fa2Sopenharmony_ci 99fb299fa2Sopenharmony_ci buff_.width = vinfo_.xres; 100fb299fa2Sopenharmony_ci buff_.height = vinfo_.yres; 101fb299fa2Sopenharmony_ci buff_.size = finfo_.line_length * vinfo_.yres; 102fb299fa2Sopenharmony_ci buff_.vaddr = mmap(nullptr, finfo_.smem_len, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); 103fb299fa2Sopenharmony_ci if (buff_.vaddr == MAP_FAILED) { 104fb299fa2Sopenharmony_ci LOG(ERROR) << "failed to mmap framebuffer"; 105fb299fa2Sopenharmony_ci close(fd); 106fb299fa2Sopenharmony_ci return false; 107fb299fa2Sopenharmony_ci } 108fb299fa2Sopenharmony_ci (void)memset_s(buff_.vaddr, finfo_.smem_len, 0, finfo_.smem_len); 109fb299fa2Sopenharmony_ci fd_ = fd; 110fb299fa2Sopenharmony_ci return true; 111fb299fa2Sopenharmony_ci} 112fb299fa2Sopenharmony_ci 113fb299fa2Sopenharmony_civoid FbdevDriver::Flip(const uint8_t *buf) 114fb299fa2Sopenharmony_ci{ 115fb299fa2Sopenharmony_ci if (fd_ < 0) { 116fb299fa2Sopenharmony_ci return; 117fb299fa2Sopenharmony_ci } 118fb299fa2Sopenharmony_ci UiRotation::GetInstance().RotateBuffer(buf, static_cast<uint8_t *>(buff_.vaddr), buff_.size); 119fb299fa2Sopenharmony_ci if (ioctl(fd_, FBIOPAN_DISPLAY, &vinfo_) < 0) { 120fb299fa2Sopenharmony_ci LOG(ERROR) << "failed to display fb0!"; 121fb299fa2Sopenharmony_ci } 122fb299fa2Sopenharmony_ci} 123fb299fa2Sopenharmony_ci 124fb299fa2Sopenharmony_civoid FbdevDriver::GetGrSurface(GrSurface &surface) 125fb299fa2Sopenharmony_ci{ 126fb299fa2Sopenharmony_ci surface.height = static_cast<int>(vinfo_.yres); 127fb299fa2Sopenharmony_ci surface.rowBytes = finfo_.line_length; 128fb299fa2Sopenharmony_ci surface.pixelBytes = vinfo_.bits_per_pixel / 8; // 8: byte bit len 129fb299fa2Sopenharmony_ci surface.width = static_cast<int>(surface.rowBytes / surface.pixelBytes); 130fb299fa2Sopenharmony_ci} 131fb299fa2Sopenharmony_ci 132fb299fa2Sopenharmony_civoid FbdevDriver::Blank(bool blank) 133fb299fa2Sopenharmony_ci{ 134fb299fa2Sopenharmony_ci FbPowerContrl(fd_, !blank); 135fb299fa2Sopenharmony_ci if (blankHook_ != nullptr) { 136fb299fa2Sopenharmony_ci blankHook_(fd_, blank); 137fb299fa2Sopenharmony_ci } 138fb299fa2Sopenharmony_ci} 139fb299fa2Sopenharmony_ci 140fb299fa2Sopenharmony_civoid FbdevDriver::Exit(void) 141fb299fa2Sopenharmony_ci{ 142fb299fa2Sopenharmony_ci ReleaseFb(&buff_); 143fb299fa2Sopenharmony_ci} 144fb299fa2Sopenharmony_ci 145fb299fa2Sopenharmony_civoid FbdevDriver::SetDevPath(const std::string &devPath) 146fb299fa2Sopenharmony_ci{ 147fb299fa2Sopenharmony_ci devPath_ = devPath; 148fb299fa2Sopenharmony_ci} 149fb299fa2Sopenharmony_ci 150fb299fa2Sopenharmony_civoid FbdevDriver::RegisterBlankHook(FbBlankHook blankHook) 151fb299fa2Sopenharmony_ci{ 152fb299fa2Sopenharmony_ci blankHook_ = blankHook; 153fb299fa2Sopenharmony_ci} 154fb299fa2Sopenharmony_ci 155fb299fa2Sopenharmony_civoid FbdevDriver::ReleaseFb(const struct FbBufferObject *fbo) 156fb299fa2Sopenharmony_ci{ 157fb299fa2Sopenharmony_ci /* 158fb299fa2Sopenharmony_ci * When fd_ isn't less than 0, then fbo->vaddr is valid and can by safely munmap. 159fb299fa2Sopenharmony_ci * this can be guaranteed by FbdevDriver::Init. 160fb299fa2Sopenharmony_ci */ 161fb299fa2Sopenharmony_ci if (fd_ < 0) { 162fb299fa2Sopenharmony_ci return; 163fb299fa2Sopenharmony_ci } 164fb299fa2Sopenharmony_ci munmap(fbo->vaddr, fbo->size); 165fb299fa2Sopenharmony_ci close(fd_); 166fb299fa2Sopenharmony_ci fd_ = -1; 167fb299fa2Sopenharmony_ci} 168fb299fa2Sopenharmony_ci 169fb299fa2Sopenharmony_cibool FbdevDriver::FbPowerContrl(int fd, bool powerOn) 170fb299fa2Sopenharmony_ci{ 171fb299fa2Sopenharmony_ci if (fd < 0) { 172fb299fa2Sopenharmony_ci return false; 173fb299fa2Sopenharmony_ci } 174fb299fa2Sopenharmony_ci if (ioctl(fd, FBIOBLANK, powerOn ? FB_BLANK_UNBLANK : FB_BLANK_POWERDOWN) < 0) { 175fb299fa2Sopenharmony_ci LOG(ERROR) << "failed to set fb0 power " << powerOn; 176fb299fa2Sopenharmony_ci return false; 177fb299fa2Sopenharmony_ci } 178fb299fa2Sopenharmony_ci return true; 179fb299fa2Sopenharmony_ci} 180fb299fa2Sopenharmony_ci} // namespace Updater 181