^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Copyright (c) 2022 Rockchip Electronics Co. Ltd.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * it6616 HDMI to MIPI CSI-2 bridge driver.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) * Author: Jau-Chih.Tseng@ite.com.tw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * Jianwei Fan <jianwei.fan@rock-chips.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * V0.0X01.0X00 first version.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) // #define DEBUG
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/clk.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/delay.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <linux/gpio/consumer.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <linux/hdmi.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <linux/i2c.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #include <linux/interrupt.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) #include <linux/of_graph.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) #include <linux/rk-camera-module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) #include <linux/timer.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) #include <linux/v4l2-dv-timings.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) #include <linux/version.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) #include <linux/videodev2.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) #include <linux/workqueue.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) #include <linux/compat.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #include <linux/regmap.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) #include <media/v4l2-controls_rockchip.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) #include <media/v4l2-ctrls.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) #include <media/v4l2-device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) #include <media/v4l2-dv-timings.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) #include <media/v4l2-event.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) #include <media/v4l2-fwnode.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) #include <media/cec.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) #define DRIVER_VERSION KERNEL_VERSION(0, 0x01, 0x00)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) static int debug;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) module_param(debug, int, 0644);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) MODULE_PARM_DESC(debug, "debug level (0-3)");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) #define IT6616_NAME "IT6616"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) #define POLL_INTERVAL_MS 100
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) #define TIMER_100MS 105
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) #define IT6616_XVCLK_FREQ 27000000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) #define IT6616_LINK_FREQ 400000000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) #define IT6616_PIXEL_RATE 400000000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) #define IT6616_MEDIA_BUS_FMT MEDIA_BUS_FMT_UYVY8_2X8
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) #define I2C_ADR_HDMI 0x90
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) #define I2C_ADR_MIPI 0xAC
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) #define I2C_ADR_EDID 0xA8
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) //define in HDMI SPEC 2.0 PAGE 84
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) #define AUDIO_SAMPLING_1024K 0x35
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) #define AUDIO_SAMPLING_768K 0x09
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) #define AUDIO_SAMPLING_512K 0x3B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) #define AUDIO_SAMPLING_384K 0x05
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) #define AUDIO_SAMPLING_256K 0x1B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) #define AUDIO_SAMPLING_192K 0x0E
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) #define AUDIO_SAMPLING_176P4K 0x0C
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) #define AUDIO_SAMPLING_128K 0x2B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) #define AUDIO_SAMPLING_96K 0x0A
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) #define AUDIO_SAMPLING_88P2K 0x08
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) #define AUDIO_SAMPLING_64K 0x0B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) #define AUDIO_SAMPLING_48K 0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) #define AUDIO_SAMPLING_44P1K 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) #define AUDIO_SAMPLING_32K 0x03
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) #define REG_RX_AVI_HB1 0x13
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) #define REG_RX_AVI_HB2 0x12
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) #define REG_RX_AVI_DB0 0x14
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) #define REG_RX_AVI_DB1 0x15
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) #define REG_RX_AVI_DB2 0x16
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) #define REG_RX_AVI_DB3 0x17
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) #define REG_RX_AVI_DB4 0x18
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) #define REG_RX_AVI_DB5 0x19
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) #define REG_RX_AVI_DB6 0x1A
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) #define REG_RX_AVI_DB7 0x1B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) #define REG_RX_AVI_DB8 0x1C
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) #define REG_RX_AVI_DB9 0x1D
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) #define REG_RX_AVI_DB10 0x1E
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) #define REG_RX_AVI_DB11 0x1F
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) #define REG_RX_AVI_DB12 0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) #define REG_RX_AVI_DB13 0x21
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) #define REG_RX_AVI_DB14 0x22
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) #define REG_RX_AVI_DB15 0x23
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) #define DP_REG_INT_STS_07 0x07
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) #define DP_REG_INT_STS_08 0x08
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) #define DP_REG_INT_STS_09 0x09
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) #define DP_REG_INT_STS_0A 0x0A
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) #define DP_REG_INT_STS_0B 0x0B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) #define DP_REG_INT_STS_0C 0x0C
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) #define DP_REG_INT_STS_0D 0x0D
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) #define DP_REG_INT_STS_0E 0x0E
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) #define DP_REG_INT_STS_0F 0x0F
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) #define DP_REG_INT_STS_2B 0x2B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) #define DP_REG_INT_STS_2C 0x2C
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) #define DP_REG_INT_STS_2D 0x2D
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) #define DP_REG_INT_MASK_07 0xD1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) #define DP_REG_INT_MASK_08 0xD2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) #define DP_REG_INT_MASK_09 0xD3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) #define DP_REG_INT_MASK_0A 0xD4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) #define DP_REG_INT_MASK_0B 0xD5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) #define DP_REG_INT_MASK_0C 0xD6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) #define DP_REG_INT_MASK_0D 0xD7
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) #define DP_REG_INT_MASK_0E 0xD8
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) #define DP_REG_INT_MASK_0F 0xD9
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) #define DP_REG_INT_MASK_10 0xDA
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) #define DP_REG_INT_MASK_11 0xDB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) #define DP_REG_INT_MASK_2D 0xDC
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) #define DP_REG_INT_MASK_2C 0xDD
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) #define DP_REG_INT_MASK_2B 0xDE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) #define BANK 0x0F
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) #define BANKM 0x07
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) #define FROM_CONFIG 0xFF
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) #define AUDIO_I2S_JUSTIFIED AUDIO_I2S_MODE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) // #define MIPI_TX_INTERFACE MIPI_DSI
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) #define MIPI_TX_INTERFACE MIPI_CSI
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) #define MIPI_TX_LANE_SWAP false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) #define MIPI_TX_PN_SWAP false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) // #define MIPI_TX_DATA_TYPE DSI_RGB_24b
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) #define MIPI_TX_DATA_TYPE CSI_YCbCr4228b
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) #define MIPI_TX_ENABLE_AUTO_ADJUST_LANE_COUNT false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) /* HDMI_RX_VIDEO_STABLE_CONDITION_V_FRAME,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) * HDMI_RX_VIDEO_STABLE_CONDITION_CLOCK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) * HDMI_RX_VIDEO_STABLE_CONDITION_H_LINE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) #define HDMI_RX_VIDEO_STABLE_CONDITION HDMI_RX_VIDEO_STABLE_CONDITION_V_FRAME
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) /* MIPI_TX_NON_CONTINUOUS_CLOCK, MIPI_TX_CONTINUOUS_CLOCK */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) #define MIPI_TX_ENABLE_CONTINUOUS_CLOCK MIPI_TX_CONTINUOUS_CLOCK
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) #define MIPI_TX_ENABLE_DSI_SYNC_EVENT false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) #define MIPI_TX_ENABLE_DSI_EOTP_PACKET false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) #define MIPI_TX_ENABLE_INITIAL_FIRE_LP_CMD true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) #define DEFAULT_RS_LEVEL 0x9F
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) #define MIPI_TX_ENABLE_MANUAL_ADJUSTED_D_PHY false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) #define MIPI_TX_LPX 2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) #define MIPI_TX_HS_PREPARE 0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) #define MIPI_TX_HS_PREPARE_ZERO 0x04
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) #define MIPI_TX_HS_TRAIL 0x07
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) #define MAX_AUDIO_SAMPLING_FREQ_ERROR_COUNT 15
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) #define HDMI_RX_DISABLE_PIXEL_REPEAT true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) #define MIPI_TX_LANE_ADJUST_THRESHOLD 30
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) #define MIPI_TX_V_LPM_LENGTH 0x200
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) #define MIPI_TX_H_LPM_LENGTH 0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) #define MIPI_TX_ENABLE_H_ENTER_LPM false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) #define MIPI_TX_ENABLE_HS_PRE_1T true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) #define MIPI_TX_ENABLE_PCLK_INV false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) #define MIPI_TX_ENABLE_MCLK_INV true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) #define MIPI_TX_ENABLE_BY_PASS true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) #define MIPI_TX_ENABLE_H_FIRE_PACKET false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) #define HDMI_RX_ENABLE_COLOR_UP_DN_FILTER true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) #define HDMI_RX_ENABLE_DITHER_FUNCTION false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) #define HDMI_RX_ENABLE_DITHER_FCNT_FUNCTION false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) #define HDMI_RX_COLOR_CLIP true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) #define HDMI_RX_CRCB_LIMIT false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) #define HDMI_RX_QUANT_4LB true
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) #define HDMI_RX_AUTO_CSC_SELECT false
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) #define LP_CMD_FIFO_SIZE 128
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) enum csc_matrix_type {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) CSCMtx_RGB2YUV_ITU601_16_235,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) CSCMtx_RGB2YUV_ITU601_00_255,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) CSCMtx_RGB2YUV_ITU709_16_235,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) CSCMtx_RGB2YUV_ITU709_00_255,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) CSCMtx_YUV2RGB_ITU601_16_235,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) CSCMtx_YUV2RGB_ITU601_00_255,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) CSCMtx_YUV2RGB_ITU709_16_235,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) CSCMtx_YUV2RGB_ITU709_00_255,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) CSCMtx_YUV2RGB_BT2020_00_255,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) CSCMtx_RGB_00_255_RGB_16_235,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) CSCMtx_RGB_16_235_RGB_00_255,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) CSCMtx_Unknown,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) MIPI_CSI,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) MIPI_DSI,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) VSC_COLOR_RGB = 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) VSC_COLOR_YUV444 = 0x01,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) VSC_COLOR_YUV422 = 0x02,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) VSC_COLOR_YUV420 = 0x03,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) VSC_COLOR_YONLY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) VSC_COLOR_RAW,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) VSC_COLOR_RESERVE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) COLOR_RGB = 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) COLOR_YUV422 = 0x01,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) COLOR_YUV444 = 0x02,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) COLOR_YUV420 = 0x03,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) COLOR_RESERVE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) COLORIMETRY_BT601 = 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) COLORIMETRY_BT709 = 0x01,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) COLORIMETRY_xvYCC601 = 0x02,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) COLORIMETRY_xvYCC709 = 0x03,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) COLORIMETRY_sYCC601 = 0x04,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) COLORIMETRY_aYCC601 = 0x05,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) COLORIMETRY_BT2020YcCbcCrc = 0x06,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) COLORIMETRY_BT2020YCbCr = 0x07,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) COLORIMETRY_RESERVE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) COLORIMETRY_sRGB = 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) COLORIMETRY_fixRGB = 0x01,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) COLORIMETRY_scRGB = 0x02,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) COLORIMETRY_aRGB = 0x03,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) COLORIMETRY_DCIP3 = 0x04,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) COLORIMETRY_CUSTOM = 0x05,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) COLORIMETRY_BT2020RGB = 0x06
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) enum mipi_csi_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) CSI_RGB10b = 0x25,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) CSI_RGB888 = 0x24,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) CSI_RGB666 = 0x23,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) CSI_RGB565 = 0x22,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) CSI_RGB555 = 0x21,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) CSI_RGB444 = 0x20,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) CSI_YCbCr4208b = 0x1A,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) CSI_YCbCr4228b = 0x1E,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) CSI_YCbCr42210b = 0x1F,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) CSI_YCbCr42212b = 0x30
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) enum mipi_dsi_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) DSI_RGB_24b = 0x3E,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) DSI_RGB_30b = 0x0D,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) DSI_RGB_36b = 0x1D,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) DSI_RGB_18b = 0x1E,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) DSI_RGB_18b_L = 0x2E,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) DSI_YCbCr_16b = 0x2C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) DSI_YCbCr_20b = 0x0C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) DSI_YCbCr_24b = 0x1C
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) enum csc_select {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) CSC_BYPASS = 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) CSC_RGB2YUV = 0x02,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) CSC_YUV2RGB = 0x03,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) enum av_mute_state {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) AV_MUTE_OFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) AV_MUTE_ON,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) AUDIO_OFF = 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) AUDIO_I2S = 0x01,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) AUDIO_SPDIF = 0x02,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) AUDIO_I2S_MODE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) AUDIO_RIGHT_JUSTIFIED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) AUDIO_LEFT_JUSTIFIED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) MIPI_TX_NON_CONTINUOUS_CLOCK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) MIPI_TX_CONTINUOUS_CLOCK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) HDMI_RX_VIDEO_STABLE_CONDITION_V_FRAME,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) HDMI_RX_VIDEO_STABLE_CONDITION_CLOCK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) HDMI_RX_VIDEO_STABLE_CONDITION_H_LINE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) enum dcs_cmd_name {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) ENTER_SLEEP_MODE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) SET_DISPLAY_OFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) EXIT_SLEEP_MODE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) SET_DISPLAY_ON,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) GET_DISPLAY_MODE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) LONG_WRITE_CMD,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) LONG_WRITE_CMD1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) DELAY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) enum mipi_lp_cmd_type {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) LP_CMD_LPDT = 0x87,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) LP_CMD_BTA = 0xFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) enum mipi_packet_size {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) SHORT_PACKET,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) LONG_PACKET,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) UNKNOWN_PACKET,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) enum mipi_tx_lp_cmd_header {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) NO_HEADER,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) CALC_HEADER,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) static const s64 link_freq_menu_items[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) IT6616_LINK_FREQ,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) struct it6616_reg_set {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) u8 ucAddr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) u8 andmask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) u8 ucValue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) struct bus_config {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) u8 lane;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) u8 type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) u8 reg23_p2m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) u8 regb0_div[3];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) union tx_p2m_delay {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) u8 tx_dsi_vsync_delay;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) u8 tx_csi_p2m_delay;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) struct bus_para {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) struct bus_config cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) u8 swap_pn;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) u8 swap_lan;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) u8 pclk_inv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) u8 mclk_inv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) u8 lpx_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) u8 mipi_tx_hs_prepare;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) u8 tx_sel_line_start;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) u8 tx_bypass;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) u8 tx_enable_hs_pre_1T;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) u8 tx_enable_h_enter_lpm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) u8 tx_vsync_delay;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) union tx_p2m_delay p2m_delay;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) u16 tx_vlpm_length;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) u16 tx_hlpm_length;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) struct mipi_bus {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) u8 lane_cnt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) u8 data_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) u8 bus_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) u32 mbus_fmt_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) struct bus_para bus_para_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) struct mipi_packet_size_data_id_map {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) u8 data_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) enum mipi_packet_size packet_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) struct mipi_packet_size_data_id_map packet_size_data_id_map[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) {0x05, SHORT_PACKET},/* dcs short write without parameter */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) {0x15, SHORT_PACKET},/* dcs short write with one parameter */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) {0x23, SHORT_PACKET},/* generic short write, 2 parameters */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) {0x29, LONG_PACKET},/* generic long write */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) {0x39, LONG_PACKET},/* dcs long write */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) {0x06, SHORT_PACKET},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) {0x16, SHORT_PACKET},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) {0x37, SHORT_PACKET},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) {0x03, SHORT_PACKET},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) {0x13, SHORT_PACKET},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) {0x04, SHORT_PACKET},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) {0x14, SHORT_PACKET},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) {0x24, SHORT_PACKET}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) struct mipi_packet {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) u8 data_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) u8 word_count_l;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) u8 word_count_h;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) u8 ecc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) struct dcs_setting_entry {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) enum dcs_cmd_name cmd_name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) enum mipi_lp_cmd_type cmd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) u8 data_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) u8 count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) u8 para_list[LP_CMD_FIFO_SIZE];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) static const struct dcs_setting_entry dcs_table[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) { /* command 0x10 with no parameter, checksum: 0x2C */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) ENTER_SLEEP_MODE, LP_CMD_LPDT, 0x05, 2, {0x10, 0x00}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) }, { /* command 0x28 with no parameter, checksum: 0x06 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) SET_DISPLAY_OFF, LP_CMD_LPDT, 0x05, 2, {0x28, 0x00}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) }, { /* command 0x11 with no parameter, checksum: 0x36 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) EXIT_SLEEP_MODE, LP_CMD_LPDT, 0x05, 2, {0x11, 0x00}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) }, { /* command 0x29 with no parameter, checksum: 0x1C */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) SET_DISPLAY_ON, LP_CMD_LPDT, 0x05, 2, {0x29, 0x00}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) }, { /* checksum: 0x1A */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) GET_DISPLAY_MODE, LP_CMD_LPDT, 0x06, 2, {0x0D, 0x00}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) }, { /* command 0x50 with 2 parameters */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) LONG_WRITE_CMD, LP_CMD_LPDT, 0x39, 3, {0x50, 0x5A, 0x09}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) }, { /* command 0x80 with 16 parameters */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) LONG_WRITE_CMD1, LP_CMD_LPDT, 0x29, 17,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) {0x80, 0x5A, 0x51, 0xB5, 0x2A, 0x6C, 0x35,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 0x4B, 0x01, 0x40, 0xE1, 0x0D, 0x82, 0x20, 0x08, 0x30, 0x03}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) static const int code_to_rate_table[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 44100, 0, 48000, 32000, 0, 384000, 0, 0, 88200,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 768000, 96000, 64000, 176400, 0, 192000, 0, 0, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) 0, 0, 0, 0, 0, 0, 0, 0, 0, 256000, 0, 0, 0, 0, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128000, 0, 0, 0, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 0, 0, 0, 0, 0, 1024000, 0, 0, 0, 0, 0, 512000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) struct color_format {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) unsigned char color_mode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) unsigned char color_depth;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) unsigned char color_cea_range;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) unsigned char color_colorietry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) unsigned char color_ex_colorietry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) unsigned char content_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) struct video_info {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) u16 h_active;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) u16 v_active;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) u16 h_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) u16 v_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) u32 pclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) u32 TMDSCLK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) u32 frame_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) u16 h_front_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) u16 h_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) u16 h_back_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) u16 v_front_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) u16 v_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) u16 v_back_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) u16 interlaced;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) u16 v_sync_pol;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) u16 h_sync_pol;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) u16 ColorDepth;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) u16 VIC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) struct audio_info {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) u32 n;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) u32 cts;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) u8 channel_status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) u32 sample_freq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) u32 force_sample_freq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) struct it6616 {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) struct i2c_client *hdmi_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) struct i2c_client *mipi_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) struct i2c_client *edid_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) struct regmap *hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) struct regmap *mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) struct regmap *edid_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) u8 attr_hdmi_reg_bank;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) struct class *hdmirx_class;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) struct device *dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) struct device *classdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) struct v4l2_fwnode_bus_mipi_csi2 bus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) struct v4l2_subdev sd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) struct media_pad pad;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) struct v4l2_ctrl_handler hdl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) struct i2c_client *i2c_client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) struct mutex confctl_mutex;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) struct v4l2_ctrl *detect_tx_5v_ctrl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) struct v4l2_ctrl *audio_sampling_rate_ctrl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) struct v4l2_ctrl *audio_present_ctrl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) struct v4l2_ctrl *link_freq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) struct v4l2_ctrl *pixel_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) struct v4l2_dv_timings timings;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) struct clk *xvclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) struct gpio_desc *reset_gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) struct gpio_desc *power_gpio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) struct delayed_work work_i2c_poll;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) const char *module_facing;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) const char *module_name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) const char *len_name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) const struct it6616_mode *cur_mode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) bool nosignal;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) bool is_audio_present;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) u32 mbus_fmt_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) u8 csi_lanes_in_use;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) u32 module_index;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) u32 audio_sampling_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) bool hdmi_rx_video_stable;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) bool hdmi_rx_hdcp_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) bool mipi_tx_video_stable;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) bool mipi_tx_enable_manual_adjusted_d_phy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) u8 audio_stable;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) u8 audio_interface;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) u8 rs_level;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) struct mipi_bus mipi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) struct color_format color_fmt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) struct video_info vinfo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) struct audio_info ainfo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) u8 edid_data[256];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) u16 edid_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) u8 audio_sampling_freq_error_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) u8 audio_i2s_justified;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) u8 mipi_tx_enable_auto_adjust_lane_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) u8 mipi_tx_enable_h_fire_packet;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) u8 mipi_tx_enable_initial_fire_lp_cmd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) u8 hdmi_rx_disable_pixel_repeat;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) bool mipi_tx_enable_continuous_clock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) u8 mipi_tx_enable_mipi_output;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) u8 hdmi_rx_video_stable_condition;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) bool power_on;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) u32 rclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) u32 tx_mclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) u32 tx_rclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) u32 tx_pclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) u32 tx_mclk_ps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) struct hdmi_avi_infoframe avi_if;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) struct hdmi_avi_infoframe avi_if_prev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) enum hdmi_colorspace output_colorspace;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) static const struct v4l2_dv_timings_cap it6616_timings_cap = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) .type = V4L2_DV_BT_656_1120,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) .reserved = { 0 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) V4L2_INIT_BT_TIMINGS(1, 10000, 1, 10000, 0, 400000000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) V4L2_DV_BT_STD_CEA861 | V4L2_DV_BT_STD_DMT |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) V4L2_DV_BT_STD_GTF | V4L2_DV_BT_STD_CVT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) V4L2_DV_BT_CAP_PROGRESSIVE | V4L2_DV_BT_CAP_INTERLACED |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) V4L2_DV_BT_CAP_REDUCED_BLANKING |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) V4L2_DV_BT_CAP_CUSTOM)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) struct it6616_mode {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) u32 width;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) u32 height;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) struct v4l2_fract max_fps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) u32 hts_def;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) u32 vts_def;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) u32 exp_def;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) static const struct it6616_mode supported_modes[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) .width = 3840,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) .height = 2160,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) .denominator = 300000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) .hts_def = 4400,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) .vts_def = 2250,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) .width = 1920,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) .height = 1080,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) .denominator = 600000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) .hts_def = 2200,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) .vts_def = 1125,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) .width = 1920,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) .height = 540,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) .denominator = 600000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) .hts_def = 2200,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) .vts_def = 562,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) .width = 1280,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) .height = 720,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) .denominator = 600000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) .hts_def = 1650,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) .vts_def = 750,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) .width = 720,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) .height = 576,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) .denominator = 500000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) .hts_def = 864,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) .vts_def = 625,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) .width = 720,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) .height = 480,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) .denominator = 600000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) .hts_def = 858,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) .vts_def = 525,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) .width = 720,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) .height = 288,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) .denominator = 500000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) .hts_def = 864,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) .vts_def = 312,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) .width = 720,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) .height = 240,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) .max_fps = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) .numerator = 10000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) .denominator = 600000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) .hts_def = 858,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) .vts_def = 262,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) static const u8 default_edid[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) 0x49, 0x78, 0x01, 0x88, 0x00, 0x88, 0x88, 0x88,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) 0x1C, 0x1F, 0x01, 0x03, 0x80, 0x00, 0x00, 0x78,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) 0x0A, 0x0D, 0xC9, 0xA0, 0x57, 0x47, 0x98, 0x27,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) 0x12, 0x48, 0x4C, 0x00, 0x00, 0x00, 0x01, 0x01,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x3A,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) 0x80, 0x18, 0x71, 0x38, 0x2D, 0x40, 0x58, 0x2C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) 0x45, 0x00, 0xC4, 0x8E, 0x21, 0x00, 0x00, 0x1E,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) 0x01, 0x1D, 0x00, 0x72, 0x51, 0xD0, 0x1E, 0x20,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) 0x6E, 0x28, 0x55, 0x00, 0xC4, 0x8E, 0x21, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) 0x00, 0x1E, 0x00, 0x00, 0x00, 0xFC, 0x00, 0x54,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) 0x37, 0x34, 0x39, 0x2D, 0x66, 0x48, 0x44, 0x37,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) 0x32, 0x30, 0x0A, 0x20, 0x00, 0x00, 0x00, 0xFD,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) 0x00, 0x14, 0x78, 0x01, 0xFF, 0x1D, 0x00, 0x0A,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x01, 0x64,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) 0x02, 0x03, 0x1C, 0x71, 0x49, 0x90, 0x04, 0x02,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) 0x5F, 0x11, 0x07, 0x05, 0x16, 0x22, 0x23, 0x09,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) 0x07, 0x01, 0x83, 0x01, 0x00, 0x00, 0x65, 0x03,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) 0x0C, 0x00, 0x10, 0x00, 0x8C, 0x0A, 0xD0, 0x8A,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) 0x20, 0xE0, 0x2D, 0x10, 0x10, 0x3E, 0x96, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) 0x13, 0x8E, 0x21, 0x00, 0x00, 0x1E, 0xD8, 0x09,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) 0x80, 0xA0, 0x20, 0xE0, 0x2D, 0x10, 0x10, 0x60,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) 0xA2, 0x00, 0xC4, 0x8E, 0x21, 0x00, 0x00, 0x18,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) 0x8C, 0x0A, 0xD0, 0x90, 0x20, 0x40, 0x31, 0x20,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) 0x0C, 0x40, 0x55, 0x00, 0x48, 0x39, 0x00, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) 0x00, 0x18, 0x01, 0x1D, 0x80, 0x18, 0x71, 0x38,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) 0x2D, 0x40, 0x58, 0x2C, 0x45, 0x00, 0xC0, 0x6C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) 0x00, 0x00, 0x00, 0x18, 0x01, 0x1D, 0x80, 0x18,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) 0x71, 0x1C, 0x16, 0x20, 0x58, 0x2C, 0x25, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) 0xC0, 0x6C, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB3,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) static const struct bus_config it6616_csi_bus_cfg[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) {4, CSI_RGB10b, 0x8F, {0xEE, 0xEE, 0xEE}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) {4, CSI_RGB888, 0x23, {0x65, 0x22, 0x22}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) {4, CSI_RGB666, 0x89, {0xE8, 0xE8, 0xE8}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) {4, CSI_RGB565, 0x22, {0x63, 0x21, 0x00}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) {4, CSI_RGB555, 0x22, {0x63, 0x21, 0x00}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) {4, CSI_RGB444, 0x22, {0x63, 0x21, 0x00}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) {4, CSI_YCbCr4208b, 0x23, {0x65, 0x22, 0x22}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) {4, CSI_YCbCr4228b, 0x22, {0x63, 0x21, 0x00}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) {4, CSI_YCbCr42210b, 0x45, {0x64, 0x64, 0x64}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) {4, CSI_YCbCr42212b, 0x23, {0x65, 0x22, 0x22}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) {2, CSI_RGB10b, 0x4F, {0x6E, 0x6E, 0x6E}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) {2, CSI_RGB888, 0x13, {0x6B, 0x25, 0x25}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) {2, CSI_RGB666, 0x49, {0x68, 0x68, 0x68}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) {2, CSI_RGB565, 0x12, {0x67, 0x23, 0x01}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) {2, CSI_RGB555, 0x12, {0x67, 0x23, 0x01}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) {2, CSI_RGB444, 0x12, {0x67, 0x23, 0x01}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) {2, CSI_YCbCr4208b, 0x13, {0x6B, 0x25, 0x25}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) {2, CSI_YCbCr4228b, 0x12, {0x67, 0x23, 0x01}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) {2, CSI_YCbCr42210b, 0x25, {0x69, 0x24, 0x24}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) {2, CSI_YCbCr42212b, 0x13, {0x6B, 0x25, 0x25}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) {1, CSI_RGB10b, 0x2F, {0x7D, 0x2E, 0x2E}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) {1, CSI_RGB888, 0x03, {0x77, 0x2B, 0x05}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) {1, CSI_RGB666, 0x29, {0x71, 0x28, 0x28}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) {1, CSI_RGB565, 0x02, {0x6F, 0x27, 0x03}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) {1, CSI_RGB555, 0x02, {0x6F, 0x27, 0x03}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) {1, CSI_RGB444, 0x02, {0x6F, 0x27, 0x03}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) {1, CSI_YCbCr4208b, 0x03, {0x77, 0x2B, 0x05}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) {1, CSI_YCbCr4228b, 0x02, {0x6F, 0x27, 0x03}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) {1, CSI_YCbCr42210b, 0x15, {0x73, 0x29, 0x04}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) {1, CSI_YCbCr42212b, 0x03, {0x77, 0x2B, 0x05}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) {0, 0, 0, {0, 0, 0}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) static const struct bus_config it6616_dsi_bus_cfg[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) {4, DSI_RGB_36b, 0x19, {0x68, 0x68, 0x68}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) {4, DSI_RGB_30b, 0x2F, {0xEE, 0xEE, 0xEE}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) {4, DSI_RGB_24b, 0x03, {0x65, 0x22, 0x22}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) {4, DSI_RGB_18b_L, 0x03, {0x65, 0x22, 0x22}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) {4, DSI_RGB_18b, 0x29, {0xE8, 0xE8, 0xE8}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) {2, DSI_RGB_36b, 0x19, {0x71, 0x28, 0x28}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) {2, DSI_RGB_30b, 0x2F, {0x6E, 0x6E, 0x6E}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) {2, DSI_RGB_24b, 0x03, {0x6B, 0x25, 0x25}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) {2, DSI_RGB_18b_L, 0x03, {0x6B, 0x25, 0x25}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) {2, DSI_RGB_18b, 0x29, {0x68, 0x68, 0x68}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) {1, DSI_RGB_36b, 0x19, {0x31, 0x31, 0x08}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) {1, DSI_RGB_30b, 0x2F, {0x7D, 0x2E, 0x2E}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) {1, DSI_RGB_24b, 0x03, {0x77, 0x2B, 0x05}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) {1, DSI_RGB_18b_L, 0x03, {0x77, 0x2B, 0x05}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) {1, DSI_RGB_18b, 0x29, {0x71, 0x28, 0x28}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) //add in D0 yuv422
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) {4, DSI_YCbCr_16b, 0x02, {0x63, 0x21, 0x00}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) {4, DSI_YCbCr_20b, 0x03, {0x65, 0x22, 0x22}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) {4, DSI_YCbCr_24b, 0x03, {0x65, 0x22, 0x22}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) {2, DSI_YCbCr_16b, 0x02, {0x67, 0x23, 0x01}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) {2, DSI_YCbCr_20b, 0x03, {0x6B, 0x25, 0x25}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) {2, DSI_YCbCr_24b, 0x03, {0x6B, 0x25, 0x25}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) {1, DSI_YCbCr_16b, 0x02, {0x6F, 0x27, 0x03}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) {1, DSI_YCbCr_20b, 0x03, {0x77, 0x2B, 0x05}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) {1, DSI_YCbCr_24b, 0x03, {0x77, 0x2B, 0x05}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) {0, 0, 0, {0, 0, 0}},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) static const u8 mipi_color_space[][10] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) CSI_RGB10b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) CSI_RGB888,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) CSI_RGB666,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) CSI_RGB565,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) CSI_RGB555,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) CSI_RGB444,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) CSI_YCbCr4208b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) CSI_YCbCr4228b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) CSI_YCbCr42210b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) CSI_YCbCr42212b
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) DSI_RGB_36b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) DSI_RGB_30b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) DSI_RGB_24b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) DSI_RGB_18b_L,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) DSI_RGB_18b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) DSI_YCbCr_16b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) DSI_YCbCr_20b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) DSI_YCbCr_24b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) 0xFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) 0xFF
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) static char *mipi_color_space_name[][10] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) "CSI_RGB10b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) "CSI_RGB888",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) "CSI_RGB666",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) "CSI_RGB565",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) "CSI_RGB555",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) "CSI_RGB444",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772) "CSI_YCbCr4208b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) "CSI_YCbCr4228b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) "CSI_YCbCr42210b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) "CSI_YCbCr42212b"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) "DSI_RGB_36b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) "DSI_RGB_30b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) "DSI_RGB_24b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) "DSI_RGB_18b_L",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781) "DSI_RGB_18b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) "DSI_YCbCr_16b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) "DSI_YCbCr_20b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) "DSI_YCbCr_24b",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) "can not find color space",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) "can not find color space"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) static const u8 csc_matrix[][22] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) 0x00, 0x80, 0x10, 0xB2, 0x04, 0x65, 0x02, 0xE9, 0x00, 0x93, 0x3C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) 0x18, 0x04, 0x55, 0x3F, 0x49, 0x3D, 0x9F, 0x3E, 0x18, 0x04, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) 0x10, 0x80, 0x10, 0x09, 0x04, 0x0E, 0x02, 0xC9, 0x00, 0x0F, 0x3D,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) 0x84, 0x03, 0x6D, 0x3F, 0xAB, 0x3D, 0xD1, 0x3E, 0x84, 0x03, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) 0x00, 0x80, 0x10, 0xB8, 0x05, 0xB4, 0x01, 0x94, 0x00, 0x4A, 0x3C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) 0x17, 0x04, 0x9F, 0x3F, 0xD9, 0x3C, 0x10, 0x3F, 0x17, 0x04, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) 0x10, 0x80, 0x10, 0xEA, 0x04, 0x77, 0x01, 0x7F, 0x00, 0xD0, 0x3C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) 0x83, 0x03, 0xAD, 0x3F, 0x4B, 0x3D, 0x32, 0x3F, 0x83, 0x03, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) 0x00, 0x00, 0x00, 0x00, 0x08, 0x6B, 0x3A, 0x50, 0x3D, 0x00, 0x08,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) 0xF5, 0x0A, 0x02, 0x00, 0x00, 0x08, 0xFD, 0x3F, 0xDA, 0x0D, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) 0x04, 0x00, 0xA7, 0x4F, 0x09, 0x81, 0x39, 0xDD, 0x3C, 0x4F, 0x09,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) 0xC4, 0x0C, 0x01, 0x00, 0x4F, 0x09, 0xFD, 0x3F, 0x1F, 0x10, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) 0x00, 0x00, 0x00, 0x00, 0x08, 0x55, 0x3C, 0x88, 0x3E, 0x00, 0x08,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) 0x51, 0x0C, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x84, 0x0E, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) 0x04, 0x00, 0xA7, 0x4F, 0x09, 0xBA, 0x3B, 0x4B, 0x3E, 0x4F, 0x09,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) 0x57, 0x0E, 0x02, 0x00, 0x4F, 0x09, 0xFE, 0x3F, 0xE8, 0x10, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) 0x04, 0x00, 0xA7, 0x4F, 0x09, 0xCC, 0x3A, 0x7E, 0x3E, 0x4F, 0x09,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) 0x69, 0x0D, 0x0B, 0x00, 0x4F, 0x09, 0xFE, 0x3F, 0x1D, 0x11, 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) 0x10, 0x10, 0x00, 0xe0, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) 0xe0, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x06, 0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) 0xED, 0xED, 0x00, 0x50, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) 0x50, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x50, 0x09, 0xED
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) struct it6616_reg_set it6616_hdmi_init_table[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) {0x0F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) {0x22, 0xFF, 0x08},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) {0x22, 0xFF, 0x17},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) {0x23, 0xFF, 0x1F},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) {0x2B, 0xFF, 0x1F},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) {0x24, 0xFF, 0xF8},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) {0x22, 0xFF, 0x10},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) {0x23, 0xFF, 0xA0},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) {0x2B, 0xFF, 0xA0},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) {0x24, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) {0x2F, 0xFF, 0xAD},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) {0x34, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) {0x0F, 0xFF, 0x03},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) {0xAA, 0xFF, 0xEC},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) {0x0F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) {0x0F, 0xFF, 0x03},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) {0xAC, 0xFF, 0x40},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) {0x0F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) {0x3A, 0xFF, 0x89},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) {0x43, 0xFF, 0x01},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) {0x0F, 0xFF, 0x04},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) {0x43, 0xFF, 0x01},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) {0x3A, 0xFF, 0x89},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) {0x0F, 0xFF, 0x03},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) {0xA8, 0xFF, 0x0B},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) {0x0F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854) {0x4F, 0xFF, 0x84},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) {0x44, 0xFF, 0x19},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) {0x46, 0xFF, 0x15},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) {0x47, 0xFF, 0x88},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) {0xD9, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) {0xF0, 0xFF, 0x78},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) {0xF1, 0xFF, 0x10},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) {0x0F, 0xFF, 0x03},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) {0x3A, 0xFF, 0x02},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) {0x0F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) {0x28, 0xFF, 0x88},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) {0x6E, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866) {0x77, 0xFF, 0x87},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) {0x7B, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868) {0x86, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) {0x0F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) {0x36, 0xFF, 0x06},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871) {0x8F, 0xFF, 0x41},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872) {0x0F, 0xFF, 0x01},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) {0xC0, 0xFF, 0x42},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) {0xC4, 0x70, 3<<4},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875) {0xC4, BIT(7), 0<<7},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876) {0xC7, 0xFF, 0x7F},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877) {0xC8, 0xFF, 0x1F},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878) {0xC9, 0xFF, 0x90},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) {0xCA, 0xFF, 0x99},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) {0x0F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881) {0x86, 0x0C, 0x08},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) {0x81, BIT(7), BIT(7)},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) {BANK, BANKM, 0x01},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) {0x10, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) {0x11, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886) {0x12, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887) {0x13, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) {0x28, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) {0x29, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) {0x2A, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891) {0x2B, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892) {0x2C, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893) {0xC0, 0xC0, 0x40},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894) {BANK, BANKM, 0x03},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) {0xE3, 0xFF, 0x07},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896) {0x27, 0xFF, DEFAULT_RS_LEVEL},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897) {0x28, 0xFF, DEFAULT_RS_LEVEL},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898) {0x29, 0xFF, DEFAULT_RS_LEVEL},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) {0xA7, BIT(6), BIT(6)},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900) {0x21, BIT(2), BIT(2)},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 901) {0xF8, 0xFF, 0xC3},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 902) {0xF8, 0xFF, 0xA5},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 903) {BANK, BANKM, 0x01},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 904) {0x5F, 0xFF, 0x04},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 905) {0x58, 0xFF, 0x12},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 906) {0x58, 0xFF, 0x02},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 907) {0x5F, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 908) {BANK, BANKM, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 909) {0xF8, 0xFF, 0xFF},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 910) {BANK, BANKM, 0x04},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 911) {0x3C, BIT(5), 0x000},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 912) {BANK, BANKM, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 913) {0x91, BIT(6), BIT(6)},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 914) {BANK, BANKM, 0x03},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 915) {0xF0, 0xFF, 0xC0},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 916) {BANK, BANKM, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 917) {0x21, BIT(6), BIT(6)},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 918) {0xCE, 0x30, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 919) {BANK, BANKM, 0x04},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 920) {0xCE, 0x30, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 921) {0x42, 0xE0, 0xC0},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 922) {BANK, BANKM, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 923) {0x42, 0xE0, 0xC0},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 924) {0x7B, BIT(4), BIT(4)},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 925) {0x3C, 0x21, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 926) {0x3B, 0xFF, 0x23},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 927) {0xF6, 0xFF, 0x08},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 928) {BANK, BANKM, 0x04},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 929) {0x3C, 0x21, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 930) {0x3B, 0xFF, 0x23},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 931) {BANK, BANKM, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 932) {0x59, 0xFF, 0x00},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 933) {0xFF, 0xFF, 0xFF},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 934) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 935)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 936) static struct it6616 *g_it6616;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 937) static void it6616_format_change(struct v4l2_subdev *sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 938) static int it6616_s_ctrl_detect_tx_5v(struct v4l2_subdev *sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 939) static int it6616_s_dv_timings(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 940) struct v4l2_dv_timings *timings);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 941)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 942) static inline struct it6616 *to_it6616(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 943) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 944) return container_of(sd, struct it6616, sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 945) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 946)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 947) static u8 it6616_hdmi_read(struct regmap *regmap, u8 reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 948) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 949) unsigned int val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 950)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 951) regmap_read(regmap, reg, &val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 952)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 953) return (u8)val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 954) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 955)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 956) static int it6616_hdmi_write(struct regmap *regmap, u8 reg, u8 value)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 957) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 958) return regmap_write(regmap, reg, value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 959) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 960)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 961) static int it6616_hdmi_set(struct regmap *regmap, u8 reg, u8 mask, u8 value)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 962) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 963) return regmap_update_bits(regmap, reg, mask, value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 964) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 965)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 966) static u8 it6616_mipi_tx_read(struct regmap *regmap, u8 reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 967) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 968) unsigned int val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 969)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 970) regmap_read(regmap, reg, &val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 971)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 972) return (u8)val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 973) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 974)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 975) static int it6616_mipi_tx_write(struct regmap *regmap, u8 reg, u8 value)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 976) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 977) return regmap_write(regmap, reg, value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 978) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 979)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 980) static int it6616_mipi_tx_set_bits(struct regmap *regmap, u8 reg, u8 mask, u8 value)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 981) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 982) return regmap_update_bits(regmap, reg, mask, value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 983) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 984)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 985) static int it6616_hdmi_edid_read(struct regmap *regmap, u8 *edid, int start, int length)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 986) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 987) return regmap_bulk_read(regmap, start, edid, length);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 988) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 989)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 990) static int it6616_hdmi_edid_write(struct regmap *regmap, u8 *edid, int start, int length)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 991) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 992) return regmap_bulk_write(regmap, start, edid, length);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 993) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 994)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 995) static void it6616_hdmi_chgbank(struct regmap *regmap, u8 bank)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 996) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 997) it6616_hdmi_set(regmap, 0x0F, 0x07, (u8)(bank & 0x07));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 998) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 999)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1000) static void it6616_hdim_write_table(struct regmap *regmap, struct it6616_reg_set *tdata)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1001) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1002) while (tdata->ucAddr != 0xff) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1003) if (tdata->andmask == 0xff)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1004) it6616_hdmi_write(regmap, tdata->ucAddr, tdata->ucValue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1005) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1006) it6616_hdmi_set(regmap, tdata->ucAddr, tdata->andmask, tdata->ucValue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1007) tdata++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1008) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1009) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1010)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1011) static bool it6616_mipi_tx_get_video_stable(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1012) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1013) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1014) u8 reg09h;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1015)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1016) reg09h = it6616_mipi_tx_read(mipi, 0x09);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1017)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1018) return !!(reg09h & 0x40);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1019) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1020)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1021) static void it6616_mipitx_init_bus_para(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1022) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1023) struct bus_para *bus_para = &it6616->mipi.bus_para_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1024) u8 lpx = 0x03, mipi_tx_hs_prepare = 0x01;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1025)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1026) bus_para->swap_pn = MIPI_TX_PN_SWAP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1027) bus_para->swap_lan = MIPI_TX_LANE_SWAP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1028) bus_para->pclk_inv = MIPI_TX_ENABLE_PCLK_INV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1029) bus_para->mclk_inv = MIPI_TX_ENABLE_MCLK_INV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1030) bus_para->lpx_num =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1031) it6616->mipi_tx_enable_manual_adjusted_d_phy ? MIPI_TX_LPX : lpx;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1032) bus_para->mipi_tx_hs_prepare =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1033) it6616->mipi_tx_enable_manual_adjusted_d_phy ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1034) MIPI_TX_HS_PREPARE : mipi_tx_hs_prepare;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1035) bus_para->tx_sel_line_start = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1036) bus_para->tx_bypass = MIPI_TX_ENABLE_BY_PASS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1037) bus_para->tx_enable_hs_pre_1T = MIPI_TX_ENABLE_HS_PRE_1T;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1038) bus_para->tx_vlpm_length = MIPI_TX_V_LPM_LENGTH;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1039) bus_para->tx_hlpm_length = MIPI_TX_H_LPM_LENGTH;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1040) bus_para->tx_enable_h_enter_lpm = MIPI_TX_ENABLE_H_ENTER_LPM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1041) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1042)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1043) static int it6616_get_dcs_ecc(int dcshead)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1044) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1045) int q0, q1, q2, q3, q4, q5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1046)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1047) q0 = ((dcshead >> 0) & (0x01)) ^ ((dcshead >> 1) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1048) ((dcshead >> 2) & (0x01)) ^ ((dcshead >> 4) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1049) ((dcshead >> 5) & (0x01)) ^ ((dcshead >> 7) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1050) ((dcshead >> 10) & (0x01)) ^ ((dcshead >> 11) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1051) ((dcshead >> 13) & (0x01)) ^ ((dcshead >> 16) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1052) ((dcshead >> 20) & (0x01)) ^ ((dcshead >> 21) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1053) ((dcshead >> 22) & (0x01)) ^ ((dcshead >> 23) & (0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1054) q1 = ((dcshead >> 0) & (0x01)) ^ ((dcshead >> 1) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1055) ((dcshead >> 3) & (0x01)) ^ ((dcshead >> 4) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1056) ((dcshead >> 6) & (0x01)) ^ ((dcshead >> 8) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1057) ((dcshead >> 10) & (0x01)) ^ ((dcshead >> 12) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1058) ((dcshead >> 14) & (0x01)) ^ ((dcshead >> 17) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1059) ((dcshead >> 20) & (0x01)) ^ ((dcshead >> 21) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1060) ((dcshead >> 22) & (0x01)) ^ ((dcshead >> 23) & (0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1061) q2 = ((dcshead >> 0) & (0x01)) ^ ((dcshead >> 2) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1062) ((dcshead >> 3) & (0x01)) ^ ((dcshead >> 5) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1063) ((dcshead >> 6) & (0x01)) ^ ((dcshead >> 9) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1064) ((dcshead >> 11) & (0x01)) ^ ((dcshead >> 12) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1065) ((dcshead >> 15) & (0x01)) ^ ((dcshead >> 18) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1066) ((dcshead >> 20) & (0x01)) ^ ((dcshead >> 21) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1067) ((dcshead >> 22) & (0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1068) q3 = ((dcshead >> 1) & (0x01)) ^ ((dcshead >> 2) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1069) ((dcshead >> 3) & (0x01)) ^ ((dcshead >> 7) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1070) ((dcshead >> 8) & (0x01)) ^ ((dcshead >> 9) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1071) ((dcshead >> 13) & (0x01)) ^ ((dcshead >> 14) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1072) ((dcshead >> 15) & (0x01)) ^ ((dcshead >> 19) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1073) ((dcshead >> 20) & (0x01)) ^ ((dcshead >> 21) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1074) ((dcshead >> 23) & (0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1075) q4 = ((dcshead >> 4) & (0x01)) ^ ((dcshead >> 5) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1076) ((dcshead >> 6) & (0x01)) ^ ((dcshead >> 7) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1077) ((dcshead >> 8) & (0x01)) ^ ((dcshead >> 9) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1078) ((dcshead >> 16) & (0x01)) ^ ((dcshead >> 17) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1079) ((dcshead >> 18) & (0x01)) ^ ((dcshead >> 19) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1080) ((dcshead >> 20) & (0x01)) ^ ((dcshead >> 22) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1081) ((dcshead >> 23) & (0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1082) q5 = ((dcshead >> 10) & (0x01)) ^ ((dcshead >> 11) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1083) ((dcshead >> 12) & (0x01)) ^ ((dcshead >> 13) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1084) ((dcshead >> 14) & (0x01)) ^ ((dcshead >> 15) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1085) ((dcshead >> 16) & (0x01)) ^ ((dcshead >> 17) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1086) ((dcshead >> 18) & (0x01)) ^ ((dcshead >> 19) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1087) ((dcshead >> 21) & (0x01)) ^ ((dcshead >> 22) & (0x01)) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1088) ((dcshead >> 23) & (0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1089)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1090) return (q0 + (q1 << 1) + (q2 << 2) + (q3 << 3) + (q4 << 4) + (q5 << 5));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1091) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1092)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1093) static int it6616_dcs_crc8t(int crcq16b, const u8 crc8bin)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1094) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1095) int lfsrout = 0, lfsr[16], i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1096)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1097) lfsr[15] = ((crc8bin >> 7) & 0x01) ^ ((crc8bin >> 3) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1098) ((crcq16b >> 7) & 0x01) ^ ((crcq16b >> 3) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1099) lfsr[14] = ((crc8bin >> 6) & 0x01) ^ ((crc8bin >> 2) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1100) ((crcq16b >> 6) & 0x01) ^ ((crcq16b >> 2) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1101) lfsr[13] = ((crc8bin >> 5) & 0x01) ^ ((crc8bin >> 1) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1102) ((crcq16b >> 5) & 0x01) ^ ((crcq16b >> 1) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1103) lfsr[12] = ((crc8bin >> 4) & 0x01) ^ ((crc8bin >> 0) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1104) ((crcq16b >> 4) & 0x01) ^ ((crcq16b >> 0) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1105) lfsr[11] = ((crc8bin >> 3) & 0x01) ^ ((crcq16b >> 3) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1106) lfsr[10] = ((crc8bin >> 7) & 0x01) ^ ((crc8bin >> 3) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1107) ((crc8bin >> 2) & 0x01) ^ ((crcq16b >> 7) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1108) ((crcq16b >> 3) & 0x01) ^ ((crcq16b >> 2) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1109) lfsr[9] = ((crc8bin >> 6) & 0x01) ^ ((crc8bin >> 2) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1110) ((crc8bin >> 1) & 0x01) ^ ((crcq16b >> 6) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1111) ((crcq16b >> 2) & 0x01) ^ ((crcq16b >> 1) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1112) lfsr[8] = ((crc8bin >> 5) & 0x01) ^ ((crc8bin >> 1) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1113) ((crc8bin >> 0) & 0x01) ^ ((crcq16b >> 5) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1114) ((crcq16b >> 1) & 0x01) ^ ((crcq16b >> 0) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1115) lfsr[7] = ((crc8bin >> 4) & 0x01) ^ ((crc8bin >> 0) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1116) ((crcq16b >> 15) & 0x01) ^ ((crcq16b >> 4) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1117) ((crcq16b >> 0) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1118) lfsr[6] = ((crc8bin >> 3) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1119) ((crcq16b >> 14) & 0x01) ^ ((crcq16b >> 3) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1120) lfsr[5] = ((crc8bin >> 2) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1121) ((crcq16b >> 13) & 0x01) ^ ((crcq16b >> 2) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1122) lfsr[4] = ((crc8bin >> 1) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1123) ((crcq16b >> 12) & 0x01) ^ ((crcq16b >> 1) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1124) lfsr[3] = ((crc8bin >> 7) & 0x01) ^ ((crc8bin >> 3) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1125) ((crc8bin >> 0) & 0x01) ^ ((crcq16b >> 11) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1126) ((crcq16b >> 7) & 0x01) ^ ((crcq16b >> 3) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1127) ((crcq16b >> 0) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1128) lfsr[2] = ((crc8bin >> 6) & 0x01) ^ ((crc8bin >> 2) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1129) ((crcq16b >> 10) & 0x01) ^ ((crcq16b >> 6) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1130) ((crcq16b >> 2) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1131) lfsr[1] = ((crc8bin >> 5) & 0x01) ^ ((crc8bin >> 1) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1132) ((crcq16b >> 9) & 0x01) ^ ((crcq16b >> 5) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1133) ((crcq16b >> 1) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1134) lfsr[0] = ((crc8bin >> 4) & 0x01) ^ ((crc8bin >> 0) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1135) ((crcq16b >> 8) & 0x01) ^ ((crcq16b >> 4) & 0x01) ^
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1136) ((crcq16b >> 0) & 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1137)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1138) for (i = 0; i < ARRAY_SIZE(lfsr); i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1139) lfsrout = lfsrout + (lfsr[i] << i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1140)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1141) return lfsrout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1142) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1143)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1144) static int it6616_get_dcs_crc(int bytenum, const u8 *crcbyte)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1145) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1146) int i, crctemp = 0xFFFF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1147)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1148) for (i = 0; i <= bytenum - 1; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1149) crctemp = it6616_dcs_crc8t(crctemp, crcbyte[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1150)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1151) return crctemp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1152) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1154) static void it6616_mipi_tx_setup_long_packet_header(struct mipi_packet *pheader,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1155) u32 word_count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1156) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1157) int header;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1158)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1159) pheader->word_count_h = word_count >> 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1160) pheader->word_count_l = (u8)word_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1161) header = pheader->data_id | pheader->word_count_h << 16 | pheader->word_count_l << 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1162) pheader->ecc = it6616_get_dcs_ecc(header);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1163) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1164)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1165) static enum mipi_packet_size it6616_mipi_tx_get_packet_size(struct it6616 *it6616,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1166) const struct dcs_setting_entry *dcs_setting_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1167) enum dcs_cmd_name cmd_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1168) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1169) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1170) u8 i, size = ARRAY_SIZE(packet_size_data_id_map);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1171)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1172) for (i = 0; i < size; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1173) if (dcs_setting_table[cmd_name].data_id == packet_size_data_id_map[i].data_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1174) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1175) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1176)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1177) if (i == size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1178) if (dcs_setting_table[cmd_name].count == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1179) dev_err(dev, "error! cmd index: %d count = 0", cmd_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1180) return UNKNOWN_PACKET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1181) } else if (dcs_setting_table[cmd_name].count < 3) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1182) return SHORT_PACKET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1183) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1184) return LONG_PACKET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1185) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1186) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1187)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1188) return packet_size_data_id_map[i].packet_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1189) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1190)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1191) static void it6616_mipi_tx_get_packet_fire_state(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1192) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1193) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1194) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1195) int lp_cmd_fifo, link_data_fifo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1196)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1197) lp_cmd_fifo = it6616_mipi_tx_read(mipi, 0x71) & 0x0F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1198) link_data_fifo = it6616_mipi_tx_read(mipi, 0x72);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1199)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1200) if (lp_cmd_fifo != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1201) dev_err(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1202) "error! fire low power cmd fail, remain bytes not fire, reg0x71:0x%02x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1203) lp_cmd_fifo);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1204) if (link_data_fifo != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1205) dev_err(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1206) "error! fire link0 low power data fail, remain %d bytes not fire, reg0x72:0x%02x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1207) link_data_fifo, link_data_fifo);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1208) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1209)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1210) static void it6616_mipi_tx_setup_packet(struct it6616 *it6616, struct mipi_packet *pheader,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1211) const struct dcs_setting_entry *dcs_setting_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1212) enum dcs_cmd_name cmd_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1213) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1214) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1215) int short_cmd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1216) enum mipi_packet_size packet_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1217)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1218) pheader->data_id = dcs_setting_table[cmd_name].data_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1219) packet_size = it6616_mipi_tx_get_packet_size(it6616, dcs_setting_table, cmd_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1220)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1221) if (packet_size == UNKNOWN_PACKET) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1222) dev_err(dev, "error! unknown packet size and check dcs table parameter");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1223) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1224) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1226) if (packet_size == SHORT_PACKET) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1227) pheader->word_count_l = dcs_setting_table[cmd_name].para_list[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1228) pheader->word_count_h = dcs_setting_table[cmd_name].para_list[1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1229) short_cmd = pheader->data_id | pheader->word_count_l << 8 |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1230) pheader->word_count_h << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1231) pheader->ecc = it6616_get_dcs_ecc(short_cmd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1232) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1233)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1234) if (packet_size == LONG_PACKET)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1235) it6616_mipi_tx_setup_long_packet_header(pheader, dcs_setting_table[cmd_name].count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1236) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1237)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1238) static inline void it6616_mipi_tx_fire_packet(struct it6616 *it6616,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1239) const struct dcs_setting_entry *dcs_setting_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1240) enum dcs_cmd_name cmd_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1241) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1242) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1243)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1244) it6616_mipi_tx_write(mipi, 0x75, dcs_setting_table[cmd_name].cmd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1245) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1246)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1247) static void it6616_mipi_tx_setup_packet_process(struct it6616 *it6616,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1248) const struct dcs_setting_entry *dcs_setting_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1249) enum dcs_cmd_name cmd_name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1250) enum mipi_tx_lp_cmd_header header_select)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1251) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1252) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1253) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1254) struct v4l2_subdev *sd = &it6616->sd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1255) struct mipi_packet packet;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1256) enum mipi_packet_size packet_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1257) u32 long_packet_checksum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1258) int i, header_crc, data_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1259)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1260) if (!header_select) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1261) dev_err(dev, "no header packet");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1262)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1263) for (i = 0; i < dcs_setting_table[cmd_name].count; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1264) it6616_mipi_tx_write(mipi, 0x73, dcs_setting_table[cmd_name].para_list[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1265) v4l2_dbg(1, debug, sd, "data[%d]: 0x%02x ", i,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1266) dcs_setting_table[cmd_name].para_list[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1267) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1268)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1269) header_crc = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1270) goto short_packet;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1271) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1272) it6616_mipi_tx_setup_packet(it6616, &packet, dcs_setting_table, cmd_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1273) packet_size = it6616_mipi_tx_get_packet_size(it6616, dcs_setting_table, cmd_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1274) v4l2_dbg(1, debug, sd, "%s packet\n\r", packet_size == LONG_PACKET ? "long" : "short");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1275)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1276) for (i = 0; i < sizeof(packet); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1277) it6616_mipi_tx_write(mipi, 0x73, ((u8 *)(&packet))[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1278) v4l2_dbg(1, debug, sd, "data[%d]: 0x%02x ", i, ((u8 *)(&packet))[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1279) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1280) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1281)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1282) if (packet_size == SHORT_PACKET) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1283) header_crc = 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1284) goto short_packet;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1285) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1286)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1287) header_crc = sizeof(packet) + 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1288)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1289) long_packet_checksum = it6616_get_dcs_crc(dcs_setting_table[cmd_name].count,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1290) dcs_setting_table[cmd_name].para_list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1291) for (i = 0; i < dcs_setting_table[cmd_name].count; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1292) it6616_mipi_tx_write(mipi, 0x73, dcs_setting_table[cmd_name].para_list[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1293) v4l2_dbg(1, debug, sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1294) "cmd para: 0x%02x", dcs_setting_table[cmd_name].para_list[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1295) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1296)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1297) it6616_mipi_tx_write(mipi, 0x73, (u8)long_packet_checksum);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1298) it6616_mipi_tx_write(mipi, 0x73, (u8)(long_packet_checksum >> 8));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1299) v4l2_dbg(1, debug, sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1300) "long_packet_checksum_l: 0x%02x long_packet_checksum_h: 0x%02x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1301) (u8)long_packet_checksum, (u8)(long_packet_checksum >> 8));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1302)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1303) short_packet:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1304) data_count = dcs_setting_table[cmd_name].count + header_crc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1305)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1306) if (data_count == LP_CMD_FIFO_SIZE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1307) data_count = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1308)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1309) it6616_mipi_tx_write(mipi, 0x74, (it6616->mipi_tx_enable_h_fire_packet << 7) | data_count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1310) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1311)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1312) static void it6616_mipi_tx_write_lp_cmds(struct it6616 *it6616,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1313) const struct dcs_setting_entry *dcs_setting_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1314) int dcs_table_size, enum dcs_cmd_name start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1315) int count, enum mipi_tx_lp_cmd_header header_select)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1316) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1317) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1318) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1319) u8 header_size, i, data_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1320) u8 enable_force_lp_mode = !it6616_mipi_tx_get_video_stable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1321) u8 lp_cmd_fifo_size[] = { LP_CMD_FIFO_SIZE };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1322)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1323) it6616_mipi_tx_set_bits(mipi, 0x70, 0x03, 0x03);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1324) it6616_mipi_tx_set_bits(mipi, 0x70, 0x03, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1325)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1326) if (enable_force_lp_mode) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1327) it6616_mipi_tx_set_bits(mipi, 0x05, 0x16, 0x16);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1328) it6616_mipi_tx_set_bits(mipi, 0x05, 0x16, 0x10);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1329) it6616_mipi_tx_set_bits(mipi, 0x70, 0x04, 0x04);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1330) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1331)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1332) it6616_mipi_tx_write(mipi, 0x3D, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1333) it6616_mipi_tx_write(mipi, 0x3E, enable_force_lp_mode ? 0x00 : 0x10);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1334) it6616_mipi_tx_write(mipi, 0x3F, enable_force_lp_mode ? 0x30 : 0x90);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1335)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1336) for (i = start; i < start + count; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1337) dev_dbg(dev, "cmd:%d tx reg09:0x%02x", i, it6616_mipi_tx_read(mipi, 0x09));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1338) if (i >= dcs_table_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1339) goto complete_write_dcs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1340) if (dcs_setting_table[i].cmd_name == DELAY) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1341) msleep(dcs_setting_table[i].cmd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1342) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1343) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1344)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1345) header_size = header_select ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1346) ((it6616_mipi_tx_get_packet_size(it6616, dcs_setting_table, i) ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1347) SHORT_PACKET) ? 2 : 6) : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1348) data_count = dcs_setting_table[i].count + header_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1349)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1350) if (data_count > lp_cmd_fifo_size[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1351) dev_err(dev, "error! lp cmd: %d, exceed cmd fifo", i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1352) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1353) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1354)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1355) it6616_mipi_tx_setup_packet_process(it6616, dcs_setting_table, i, header_select);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1356) it6616_mipi_tx_fire_packet(it6616, dcs_setting_table, i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1357)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1358) if (enable_force_lp_mode)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1359) it6616_mipi_tx_get_packet_fire_state(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1360) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1361) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1362)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1363) complete_write_dcs:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1364) if (i >= dcs_table_size && (start + count > dcs_table_size))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1365) dev_err(dev, "error! exceed maximum dcs setting table index");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1366)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1367) if (enable_force_lp_mode) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1368) it6616_mipi_tx_set_bits(mipi, 0x70, 0x04, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1369) it6616_mipi_tx_set_bits(mipi, 0x05, 0x16, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1370) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1371)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1372) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1373)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1374) if (!enable_force_lp_mode)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1375) it6616_mipi_tx_get_packet_fire_state(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1376) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1377)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1378) static void it6616_enter_bus_turn_around(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1379) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1380) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1381) u8 enable_force_lp_mode = !it6616_mipi_tx_get_video_stable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1382)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1383) if (enable_force_lp_mode)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1384) it6616_mipi_tx_set_bits(mipi, 0x70, 0x04, 0x04);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1385)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1386) it6616_mipi_tx_write(mipi, 0x3E, 0x10);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1387) it6616_mipi_tx_write(mipi, 0x3F, 0x90);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1388)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1389) it6616_mipi_tx_write(mipi, 0x74, it6616->mipi_tx_enable_h_fire_packet << 7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1390) it6616_mipi_tx_write(mipi, 0x75, LP_CMD_BTA);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1391)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1392) if (enable_force_lp_mode)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1393) it6616_mipi_tx_set_bits(mipi, 0x70, 0x04, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1394) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1395)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1396) static __maybe_unused void it6616_mipi_read_panel(struct it6616 *it6616,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1397) const struct dcs_setting_entry *dcs_setting_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1398) int dcs_table_size, enum dcs_cmd_name cmd_name, u8 *buffer)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1399) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1400) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1401) int link0_data_count, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1402)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1403) it6616_mipi_tx_write_lp_cmds(it6616, dcs_setting_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1404) dcs_table_size, cmd_name, 1, CALC_HEADER);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1405) it6616_enter_bus_turn_around(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1406) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1407) link0_data_count = it6616_mipi_tx_read(mipi, 0x7A);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1408)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1409) for (i = 0; i < link0_data_count; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1410) buffer[i] = it6616_mipi_tx_read(mipi, 0x79);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1411) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1412)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1413) static int it6616_mipitx_get_bus_config(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1414) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1415) struct mipi_bus *bus = &it6616->mipi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1416) const struct bus_config *bus_config_table;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1417) struct bus_config *cfg = &bus->bus_para_config.cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1418) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1419) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1420)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1421) bus_config_table = (bus->bus_type == MIPI_CSI) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1422) it6616_csi_bus_cfg : it6616_dsi_bus_cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1423)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1424) for (i = 0; bus_config_table[i].lane; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1425) if (bus_config_table[i].lane == bus->lane_cnt &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1426) bus_config_table[i].type == bus->data_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1427)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1428) bus->bus_para_config.cfg = bus_config_table[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1429) dev_dbg(dev, "mipi_get_bus_config = %d (%s)",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1430) i, (bus->bus_type == MIPI_CSI) ? "MIPI_CSI" : "MIPI_DSI");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1431) dev_dbg(dev, "{%X, %X, %X, %X, %X ,%X}",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1432) cfg->lane,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1433) cfg->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1434) cfg->reg23_p2m,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1435) cfg->regb0_div[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1436) cfg->regb0_div[1],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1437) cfg->regb0_div[2]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1438)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1439) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1440) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1441) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1442)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1443) dev_err(dev, "mipi_get_bus_config error");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1444) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1445) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1446)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1447) static void it6616_mipitx_setup_dsi(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1448) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1449) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1450) struct bus_para *bus = &it6616->mipi.bus_para_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1451) struct bus_config *cfg = &bus->cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1452) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1453) u8 mp_lane_num = cfg->lane - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1454) u8 p2m_time_mul = 0x03;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1455) u8 p2m_time_div = 0x02;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1456) u32 mp_hs_pretime = 0x4a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1457) u32 mp_hs_endtime = 0x09;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1458) u8 mp_vid_type = cfg->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1459) u32 mclk_ps = it6616->tx_mclk_ps, tx_mclk_mhz = it6616->tx_mclk / 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1460) u32 mipi_tx_calc_hs_end_time = (6 * mclk_ps - 20 * 1000) / mclk_ps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1461) u8 reg23;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1462)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1463) reg23 = cfg->reg23_p2m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1464)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1465) p2m_time_mul = reg23 & 0x0F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1466) p2m_time_div = (reg23 & 0xF0) >> 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1467)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1468) it6616_mipi_tx_set_bits(mipi, 0x28, 0x20, bus->tx_sel_line_start << 5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1469)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1470) if (!it6616->mipi_tx_enable_manual_adjusted_d_phy) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1471) if (mp_lane_num == 3) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1472) mp_hs_pretime = (((145 + ((4 + bus->lpx_num) * 20)) * 1000 -
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1473) ((3 * mclk_ps) >> 1)) / mclk_ps);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1474) mp_hs_endtime = mipi_tx_calc_hs_end_time + 9;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1475) } else if (mp_lane_num == 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1476) mp_hs_pretime = ((((145 + ((4 + bus->lpx_num) * 20)) * 1000 -
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1477) ((3 * mclk_ps) >> 1)) / mclk_ps) >> 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1478) mp_hs_endtime = (mipi_tx_calc_hs_end_time >> 1) + 9;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1479) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1480) mp_hs_pretime = ((((145 + ((4 + bus->lpx_num) * 20)) * 1000 -
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1481) ((3 * mclk_ps) >> 1)) / mclk_ps) >> 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1482) mp_hs_endtime = (mipi_tx_calc_hs_end_time >> 2) + 9;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1483) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1484)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1485) if (mipi_tx_calc_hs_end_time <= 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1486) mp_hs_endtime = 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1487)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1488) if (tx_mclk_mhz >= 300)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1489) mp_hs_pretime += 20;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1490) else if (tx_mclk_mhz >= 250)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1491) mp_hs_pretime += 18;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1492) else if (tx_mclk_mhz >= 200)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1493) mp_hs_pretime += 15;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1494) else if (tx_mclk_mhz >= 150)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1495) mp_hs_pretime += 12;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1496) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1497) mp_hs_pretime += 9;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1498) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1499) mp_hs_pretime = MIPI_TX_HS_PREPARE_ZERO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1500) mp_hs_endtime = MIPI_TX_HS_TRAIL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1501) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1502)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1503) //dsi setting
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1504) it6616_mipi_tx_set_bits(mipi, 0x5e, 0x03, (bus->tx_vlpm_length >> 8) & 0x03);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1505) it6616_mipi_tx_set_bits(mipi, 0x5d, 0xff, bus->tx_vlpm_length & 0xFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1506) it6616_mipi_tx_set_bits(mipi, 0x5e, 0x0c, (bus->tx_hlpm_length & 0x300) >> 6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1507) it6616_mipi_tx_set_bits(mipi, 0x5f, 0xff, bus->tx_hlpm_length & 0xFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1508) it6616_mipi_tx_set_bits(mipi, 0x5e, 0x10, bus->tx_enable_h_enter_lpm << 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1509) it6616_mipi_tx_set_bits(mipi, 0x6a, 0xff, bus->p2m_delay.tx_dsi_vsync_delay);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1510) it6616_mipi_tx_set_bits(mipi, 0x6c, 0xff, mp_hs_pretime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1511) it6616_mipi_tx_set_bits(mipi, 0x6d, 0xff, mp_hs_endtime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1512) it6616_mipi_tx_set_bits(mipi, 0x5c, 0x03, (MIPI_TX_ENABLE_DSI_EOTP_PACKET << 1) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1513) MIPI_TX_ENABLE_DSI_SYNC_EVENT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1514) it6616_mipi_tx_set_bits(mipi, 0x5c, 0xf0, ((mp_vid_type & 0x30) << 2) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1515) ((mp_vid_type & 0x3) << 4));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1516) it6616_mipi_tx_set_bits(mipi, 0x60, 0x0f, p2m_time_mul);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1517) it6616_mipi_tx_set_bits(mipi, 0x61, 0x03, p2m_time_div);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1518)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1519) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1520) dev_info(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1521) "hs_prepare_zero num: 0x%02x, hs_trail num: 0x%02x, dsi_vsync_delay: 0x%02x, mipi DSI TX setting done !!!",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1522) mp_hs_pretime, mp_hs_endtime, bus->p2m_delay.tx_dsi_vsync_delay);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1523) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1524)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1525) static void it6616_mipitx_setup_csi(struct it6616 *it6616)//set_mptx
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1526) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1527) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1528) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1529) struct bus_para *bus = &it6616->mipi.bus_para_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1530) struct bus_config *cfg = &bus->cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1531) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1532) u32 mp_hs_pretime = 0x4a;// int MPHSPreTime = 0x4a;//ori:11
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1533) u32 mp_hs_endtime = 0x09;// int MPHSEndTime = 0x09;//ori:06
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1534) u8 mp_vid_type = cfg->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1535) u32 mclk_ps = it6616->tx_mclk_ps, tx_mclk_mhz = it6616->tx_mclk / 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1536) u32 mipi_tx_calc_hs_end_time = (6 * mclk_ps - 20 * 1000) / mclk_ps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1537) u8 reg23, interlace, en_fs_fr_num = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1538)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1539) reg23 = cfg->reg23_p2m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1540)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1541) interlace = (it6616_hdmi_read(hdmi, 0x98) & 0x02) >> 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1543) if (interlace)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1544) en_fs_fr_num = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1545)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1546) if (!it6616->mipi_tx_enable_manual_adjusted_d_phy) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1547) mp_hs_pretime = (((145 + ((4 + bus->lpx_num) * 20)) * 1000 -
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1548) ((3 * mclk_ps) >> 1)) / mclk_ps);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1549) mp_hs_endtime = mipi_tx_calc_hs_end_time + 9;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1550)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1551) if (mipi_tx_calc_hs_end_time <= 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1552) mp_hs_endtime = 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1553)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1554) if (tx_mclk_mhz >= 300)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1555) mp_hs_pretime += 20;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1556) else if (tx_mclk_mhz >= 250)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1557) mp_hs_pretime += 18;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1558) else if (tx_mclk_mhz >= 200)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1559) mp_hs_pretime += 15;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1560) else if (tx_mclk_mhz >= 150)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1561) mp_hs_pretime += 12;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1562) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1563) mp_hs_pretime += 9;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1564) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1565) mp_hs_pretime = MIPI_TX_HS_PREPARE_ZERO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1566) mp_hs_endtime = MIPI_TX_HS_TRAIL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1567) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1568)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1569) it6616_mipi_tx_write(mipi, 0x1F, mp_hs_endtime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1570) it6616_mipi_tx_write(mipi, 0x22, mp_hs_pretime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1571) it6616_mipi_tx_write(mipi, 0x24, 0x20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1572) it6616_mipi_tx_write(mipi, 0x25, bus->p2m_delay.tx_csi_p2m_delay);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1573) it6616_mipi_tx_set_bits(mipi, 0x26, 0x20, (en_fs_fr_num << 5));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1574) it6616_mipi_tx_write(mipi, 0x27, 0x02);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1575) it6616_mipi_tx_write(mipi, 0x20, mp_vid_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1576) it6616_mipi_tx_write(mipi, 0x23, reg23);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1577)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1578) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1579) dev_info(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1580) "hs_prepare_zero num: 0x%02x, hs_trail num: 0x%02x, tx_csi_p2m_delay: 0x%02x, mipi CSI TX setting done !!!",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1581) mp_hs_pretime, mp_hs_endtime, bus->p2m_delay.tx_csi_p2m_delay);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1582) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1583)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1584) static u8 it6616_mipi_tx_find_color_space_name_index(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1585) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1586) u8 i, csi_dsi_index = (it6616->mipi.bus_type == MIPI_CSI) ? 0 : 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1587)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1588) for (i = 0; i < ARRAY_SIZE(mipi_color_space[0]); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1589) if (it6616->mipi.data_type == mipi_color_space[csi_dsi_index][i])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1590) return i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1591) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1592)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1593) return 0xFF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1594) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1595)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1596) static void it6616_mipitx_output_disable(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1597) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1598) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1599)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1600) it6616_mipi_tx_write(mipi, 0x05, 0x36);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1601) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1602)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1603) static void it6616_mipi_tx_output_enable(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1604) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1605) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1606)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1607) /* release reset */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1608) it6616_mipi_tx_write(mipi, 0x05, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1609) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1610)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1611) static void it6616_mipi_tx_non_continuous_clock_setup(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1612) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1613) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1614) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1615)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1616) /* enable non continuous clock */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1617) it6616_mipi_tx_set_bits(mipi, 0x44, 0x01, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1618)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1619) dev_info(dev, "set mipi tx non continuous clock");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1620) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1621)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1622) static void it6616_mipitx_output_setup(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1623) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1624) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1625) struct bus_para *bus = &it6616->mipi.bus_para_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1626) struct bus_config *cfg = &bus->cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1627) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1628) u8 color_space_name_index = it6616_mipi_tx_find_color_space_name_index(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1629) u8 bus_type_index = ((it6616->mipi.bus_type == MIPI_CSI) ? 0 : 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1630) u8 regb0, mplldiv, mprediv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1631) u32 mclk_MHz;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1632) u32 pclk = it6616->vinfo.pclk / 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1633)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1634) if (it6616->mipi_tx_enable_auto_adjust_lane_count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1635) it6616->mipi.lane_cnt = it6616->csi_lanes_in_use;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1636)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1637) adjust_lane_count:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1638) dev_info(dev, "%s", bus_type_index ? "MIPI_DSI" : "MIPI_CSI");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1639) dev_info(dev, "color space: %s", (color_space_name_index != 0xFF) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1640) mipi_color_space_name[bus_type_index][color_space_name_index] : "not find match");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1641) dev_info(dev, "lan_num: %d, swap_pn: %d", it6616->mipi.lane_cnt, bus->swap_pn);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1642) dev_info(dev, "swap_lan: %d, pclk_inv: %d", bus->swap_lan, bus->pclk_inv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1643) dev_info(dev, "mclk_inv: %d, lpx_num: %d", bus->mclk_inv, bus->lpx_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1644)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1645) it6616_mipitx_get_bus_config(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1646)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1647) if (pclk > 200)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1648) regb0 = cfg->regb0_div[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1649) else if (pclk > 100)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1650) regb0 = cfg->regb0_div[1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1651) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1652) regb0 = cfg->regb0_div[2];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1653)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1654) mprediv = regb0 >> 5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1655) mplldiv = regb0 & 0x1F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1656)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1657) dev_dbg(dev, "prediv: 0x%02x, plldiv: 0x%02x", mprediv, mplldiv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1658)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1659) mclk_MHz = ((pclk) * (mplldiv + 1)) >> 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1660) mclk_MHz = mclk_MHz / (mprediv + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1661) it6616->tx_mclk = mclk_MHz * 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1662) it6616->tx_mclk_ps = (2000 * (mprediv + 1) * 1000) / ((pclk) * (mplldiv + 1));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1663) dev_info(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1664) "mclk_ns: %d.%d ns, mclk: %d MHz, pclk: %d MHz",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1665) it6616->tx_mclk_ps / 1000, it6616->tx_mclk_ps % 1000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1666) it6616->tx_mclk / 1000, pclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1667)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1668) if (it6616->mipi_tx_enable_auto_adjust_lane_count) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1669) if (mclk_MHz < MIPI_TX_LANE_ADJUST_THRESHOLD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1670) it6616->mipi.lane_cnt = (it6616->mipi.lane_cnt == 4) ? 2 : 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1671) dev_info(dev, "mclk < %d MHz, adjust to lan_num: %d",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1672) MIPI_TX_LANE_ADJUST_THRESHOLD, it6616->mipi.lane_cnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1673) goto adjust_lane_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1674) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1675) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1676)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1677) if (it6616->tx_mclk > 310000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1678) bus->mclk_inv = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1679)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1680) it6616_mipi_tx_set_bits(mipi, 0x28, 0x0c, (bus->swap_pn << 3) | (bus->swap_lan << 2));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1681) it6616_mipi_tx_set_bits(mipi, 0x10, BIT(2), bus->pclk_inv << 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1682)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1683) switch (it6616_mipi_tx_read(mipi, 0x04)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1684) case 0xC0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1685) it6616_mipi_tx_set_bits(mipi, 0x10, BIT(1), bus->mclk_inv << 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1686) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1687) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1688) it6616_mipi_tx_set_bits(mipi, 0x11, BIT(3), bus->mclk_inv << 3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1689) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1690)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1691) it6616_mipi_tx_set_bits(mipi, 0x8c, 0x40, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1692) it6616_mipi_tx_set_bits(mipi, 0x47, 0xf0, bus->mipi_tx_hs_prepare << 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1693) it6616_mipi_tx_set_bits(mipi, 0x44, 0x04, bus->tx_enable_hs_pre_1T << 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1694) it6616_mipi_tx_set_bits(mipi, 0x21, 0x30, (it6616->mipi.lane_cnt - 1) << 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1695)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1696) dev_dbg(dev, "set hs_prepare num: 0x%02x, hs_lpx num: 0x%02x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1697) bus->mipi_tx_hs_prepare, bus->lpx_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1698)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1699) if ((pclk < (10 * (mprediv + 1))) || (pclk > (100 * (mprediv + 1))))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1700) dev_err(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1701) "MPTX PHY setting wrong, need to reset parameter for TXPHY!!!");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1702)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1703) if (it6616->mipi.bus_type == MIPI_CSI) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1704) if (pclk >= (mclk_MHz * 2))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1705) bus->p2m_delay.tx_csi_p2m_delay = 0x02;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1706) else if (pclk >= mclk_MHz)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1707) bus->p2m_delay.tx_csi_p2m_delay = 0x04;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1708) else if (mclk_MHz >= (pclk * 2))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1709) bus->p2m_delay.tx_csi_p2m_delay = 0x0a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1710) else if ((mclk_MHz * 2) >= (pclk * 3))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1711) bus->p2m_delay.tx_csi_p2m_delay = 0x08;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1712) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1713) bus->p2m_delay.tx_csi_p2m_delay = 0x04;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1714) it6616_mipitx_setup_csi(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1715) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1716) if (pclk >= (mclk_MHz * 2))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1717) bus->p2m_delay.tx_dsi_vsync_delay = 0x02;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1718) else if (pclk >= mclk_MHz)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1719) bus->p2m_delay.tx_dsi_vsync_delay = 0x04;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1720) else if (mclk_MHz >= (pclk * 2))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1721) bus->p2m_delay.tx_dsi_vsync_delay = 0x0a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1722) else if ((mclk_MHz * 2) >= (pclk * 3))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1723) bus->p2m_delay.tx_dsi_vsync_delay = 0x08;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1724) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1725) bus->p2m_delay.tx_dsi_vsync_delay = 0x04;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1726) it6616_mipitx_setup_dsi(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1727) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1728)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1729) if (!it6616->mipi_tx_enable_continuous_clock)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1730) it6616_mipi_tx_non_continuous_clock_setup(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1731)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1732) /* setup mipi-tx-afe */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1733) it6616_mipi_tx_write(mipi, 0xb0, regb0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1734)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1735) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1736) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1737)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1738) static void it6616_enable_mipi(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1739) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1740) it6616_mipitx_output_setup(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1741) it6616_mipi_tx_output_enable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1742) it6616->mipi_tx_enable_mipi_output = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1743) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1744)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1745) static void it6616_disable_mipi(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1746) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1747) it6616_mipitx_output_disable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1748) it6616->mipi_tx_enable_mipi_output = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1749) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1750)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1751) static void it6616_mipi_tx_get_support_format(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1752) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1753) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1754) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1755) u8 mipi_intput_color = it6616->mipi.data_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1756) u8 color_space_name_index;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1757) u8 bus_type_index = ((it6616->mipi.bus_type == MIPI_CSI) ? 0 : 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1758)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1759) if (it6616->mipi.bus_type == MIPI_CSI) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1760) switch (mipi_intput_color) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1761) case CSI_RGB10b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1762) dev_dbg(dev, "csi not support CSI_RGB10b");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1763) it6616->mipi.data_type = CSI_RGB888;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1764) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1765)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1766) case CSI_YCbCr42212b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1767) dev_dbg(dev, "csi not support CSI_YCbCr42212b");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1768) it6616->mipi.data_type = CSI_YCbCr4228b;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1769) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1770)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1771) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1772) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1773) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1774)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1775) color_space_name_index = it6616_mipi_tx_find_color_space_name_index(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1776)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1777) if (color_space_name_index != 0xFF)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1778) dev_dbg(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1779) "will set %s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1780) mipi_color_space_name[bus_type_index][color_space_name_index]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1781) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1782) dev_err(dev, "error not find match color space");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1783) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1784) if (it6616_mipi_tx_read(mipi, 0x04) == 0xC0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1785) if ((mipi_intput_color == DSI_YCbCr_16b) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1786) (mipi_intput_color == DSI_YCbCr_20b) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1787) (mipi_intput_color == DSI_YCbCr_24b)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1788) mipi_intput_color = it6616->mipi.data_type = DSI_RGB_24b;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1789) dev_dbg(dev, "0xC0 MIPI DSI only support RGB, using: DSI_RGB_24b(%d)",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1790) mipi_intput_color);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1791) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1792) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1793) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1794) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1795)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1796) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1797) * mipi rx need pn swap and let first bit data(after SOT) will be rising edge
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1798) * can use in it6616_mipitx_initial function before it6616_mipi_tx_write_lp_cmds
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1799) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1800) static __maybe_unused void it6616_mipi_tx_rk_fix_first_bit_issue(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1801) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1802) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1803)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1804) it6616_mipi_tx_write(mipi, 0x05, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1805) it6616_mipi_tx_set_bits(mipi, 0x28, 0x08, 0x08);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1806) it6616_mipi_tx_set_bits(mipi, 0x70, 0x04, 0x04);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1807) it6616_mipi_tx_set_bits(mipi, 0x28, 0x08, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1808) it6616_mipi_tx_set_bits(mipi, 0x70, 0x04, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1809) it6616_mipi_tx_write(mipi, 0x05, 0x36);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1810) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1811)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1812) static void it6616_mipitx_initial(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1813) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1814) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1815) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1816) struct bus_para *bus = &it6616->mipi.bus_para_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1817)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1818) it6616_mipi_tx_set_bits(mipi, 0x05, 0x09, 0x09);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1819) it6616_mipi_tx_write(mipi, 0x05, 0x36);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1820)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1821) it6616_mipi_tx_set_bits(mipi, 0x2A, 0x3c, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1822) it6616_mipi_tx_set_bits(mipi, 0x3c, 0x20, 0x20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1823) it6616_mipi_tx_set_bits(mipi, 0x6b, 0x01, it6616->mipi.bus_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1824) it6616_mipi_tx_set_bits(mipi, 0x10, 0x80, bus->tx_bypass << 7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1825) it6616_mipi_tx_set_bits(mipi, 0xc1, 0x03, 0x03);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1826) it6616_mipi_tx_set_bits(mipi, 0xa8, 0x01, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1827) it6616_mipi_tx_set_bits(mipi, 0x45, 0x0f, bus->lpx_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1828)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1829) if (it6616->mipi_tx_enable_initial_fire_lp_cmd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1830) it6616_mipi_tx_write_lp_cmds(it6616, dcs_table, ARRAY_SIZE(dcs_table),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1831) SET_DISPLAY_ON, 2, CALC_HEADER);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1832) it6616_mipi_tx_write(mipi, 0x05, 0x36);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1833) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1834)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1835) dev_dbg(dev, "mipi_initial chip:0x%02x", it6616_mipi_tx_read(mipi, 0x04));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1836) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1837)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1838) static bool it6616_hdmi_is_5v_on(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1839) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1840) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1841)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1842) if (it6616_hdmi_read(hdmi, 0x13) & 0x01)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1843) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1844)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1845) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1846) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1847)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1848) static bool it6616_hdmi_is_clock_stable(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1849) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1850) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1851)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1852) if (it6616_hdmi_read(hdmi, 0x13) & 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1853) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1854)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1855) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1856) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1857)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1858) static __maybe_unused bool it6616_hdmi_is_symbol_locked(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1859) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1860) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1861) u8 reg14;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1862)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1863) reg14 = it6616_hdmi_read(hdmi, 0x14);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1864) if ((reg14 & 0x38) == 0x38)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1865) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1866)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1867) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1868) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1869)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1870) static bool it6616_hdmi_is_scdt_on(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1871) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1872) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1873)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1874) if (it6616_hdmi_read(hdmi, 0x19) & BIT(7))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1875) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1876)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1877) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1878) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1879)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1880) static u8 it6616_hdmi_get_output_color_space(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1881) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1882) u8 hdmi_output_color = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1883) u8 mipi_intput_color = it6616->mipi.data_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1884)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1885) if (it6616->mipi.bus_type == MIPI_CSI) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1886) switch (mipi_intput_color) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1887) case CSI_RGB10b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1888) case CSI_RGB888:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1889) case CSI_RGB666:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1890) case CSI_RGB565:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1891) case CSI_RGB555:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1892) case CSI_RGB444:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1893) hdmi_output_color = HDMI_COLORSPACE_RGB;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1894) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1895) case CSI_YCbCr4208b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1896) hdmi_output_color = HDMI_COLORSPACE_YUV420;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1897) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1898) case CSI_YCbCr4228b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1899) case CSI_YCbCr42210b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1900) case CSI_YCbCr42212b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1901) hdmi_output_color = HDMI_COLORSPACE_YUV422;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1902) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1903) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1904) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1905) switch (mipi_intput_color) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1906) case DSI_RGB_36b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1907) case DSI_RGB_30b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1908) case DSI_RGB_24b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1909) case DSI_RGB_18b_L:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1910) case DSI_RGB_18b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1911) hdmi_output_color = HDMI_COLORSPACE_RGB;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1912) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1913) case DSI_YCbCr_16b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1914) case DSI_YCbCr_20b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1915) case DSI_YCbCr_24b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1916) hdmi_output_color = HDMI_COLORSPACE_YUV422;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1917) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1918) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1919) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1920) it6616->output_colorspace = hdmi_output_color;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1921)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1922) return hdmi_output_color;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1923) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1924)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1925) static void it6616_hdmi_edid_ram_get(struct it6616 *it6616, u8 *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1926) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1927) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1928) struct regmap *edid = it6616->edid_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1929)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1930) it6616_hdmi_write(hdmi, 0x4B, (I2C_ADR_EDID | 0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1931) it6616_hdmi_edid_read(edid, buf, 0, 256);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1932) it6616_hdmi_write(hdmi, 0x4B, (I2C_ADR_EDID));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1933) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1934)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1935) static void it6616_hdmi_edid_ram_update_chksum(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1936) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1937) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1938) u16 sum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1939) u8 offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1940) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1941)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1942) // cal block 0 sum
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1943) sum = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1944) for (i = 0 ; i < 127 ; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1945) sum += it6616->edid_data[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1946) sum = (0x100 - sum) & 0xFF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1947)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1948) it6616_hdmi_write(hdmi, 0xC9, sum);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1949)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1950) // cal block 1 sum
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1951) sum = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1952) offset = it6616_hdmi_read(hdmi, 0xC6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1953) for (i = 128; i < 128 + 127; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1954) sum += it6616->edid_data[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1955)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1956) sum -= it6616->edid_data[offset];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1957) sum -= it6616->edid_data[offset + 1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1958) sum += it6616_hdmi_read(hdmi, 0xC7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1959) sum += it6616_hdmi_read(hdmi, 0xC8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1960) sum = (0x100 - sum) & 0xFF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1961)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1962) it6616_hdmi_write(hdmi, 0xCA, sum);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1963) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1964)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1965) static void it6616_hdmi_edid_ram_init(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1966) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1967) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1968) struct regmap *edid = it6616->edid_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1969) unsigned int phy_addr_off;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1970) u16 addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1971)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1972) // write data to EDID RAM
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1973) it6616_hdmi_write(hdmi, 0x4B, (I2C_ADR_EDID | 0x01));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1974) it6616_hdmi_edid_write(edid, it6616->edid_data, 0, it6616->edid_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1975) it6616_hdmi_write(hdmi, 0x4B, (I2C_ADR_EDID));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1976)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1977) // update physical address for VSDB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1978) addr = cec_get_edid_phys_addr(it6616->edid_data, it6616->edid_len, &phy_addr_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1979) if (addr != CEC_PHYS_ADDR_INVALID) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1980) it6616_hdmi_write(hdmi, 0xC6, (u8)phy_addr_off); // VSDB start address
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1981) it6616_hdmi_write(hdmi, 0xC7, (addr >> 8) & 0xFF); // addr AB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1982) it6616_hdmi_write(hdmi, 0xC8, addr & 0xFF); // addr CD
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1983) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1984)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1985) // recalculate block0/block1 checksum
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1986) it6616_hdmi_edid_ram_update_chksum(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1987)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1988) it6616_hdmi_set(hdmi, 0xC5, 0x10, 0x10);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1989) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1990) it6616_hdmi_set(hdmi, 0xC5, 0x10, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1991) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1992)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1993) static void it6616_hdmi_video_reset(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1994) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1995) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1996)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1997) it6616_hdmi_set(hdmi, 0x22, BIT(0), BIT(0));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1998) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1999) it6616_hdmi_set(hdmi, 0x22, BIT(0), 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2000) it6616_hdmi_set(hdmi, 0x10, BIT(1), BIT(1)); // clear vidstable change INT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2001) it6616_hdmi_set(hdmi, 0x12, BIT(7), BIT(7)); // clear vidstable change INT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2002) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2003)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2004) static void it6616_hdmi_edid_ram_enable(struct it6616 *it6616, u8 enabled)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2005) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2006) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2007)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2008) if (enabled)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2009) it6616_hdmi_set(hdmi, 0xC5, 0x3F, 0x02);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2010) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2011) it6616_hdmi_set(hdmi, 0xC5, 0x3F, 0x13);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2012) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2013)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2014) static void it6616_hdmi_rx_get_video_info(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2015) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2016) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2017) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2018) u16 h_sync_pol, v_sync_pol, interlaced;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2019) u16 h_total, h_active, h_front_porch, h_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2020) u16 v_total, v_active, v_front_porch, v_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2021) u32 frame_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2022)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2023) interlaced = (it6616_hdmi_read(hdmi, 0x98) & 0x02) >> 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2024)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2025) h_total = ((it6616_hdmi_read(hdmi, 0x9C) & 0x3F) << 8) + it6616_hdmi_read(hdmi, 0x9B);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2026) h_active = ((it6616_hdmi_read(hdmi, 0x9E) & 0x3F) << 8) + it6616_hdmi_read(hdmi, 0x9D);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2027) h_front_porch = ((it6616_hdmi_read(hdmi, 0xA1) & 0xF0) << 4) + it6616_hdmi_read(hdmi, 0xA0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2028) h_sync_w = ((it6616_hdmi_read(hdmi, 0xA1) & 0x01) << 8) + it6616_hdmi_read(hdmi, 0x9F);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2029)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2030) v_total = ((it6616_hdmi_read(hdmi, 0xA3) & 0x3F) << 8) + it6616_hdmi_read(hdmi, 0xA2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2031) v_active = ((it6616_hdmi_read(hdmi, 0xA5) & 0x3F) << 8) + it6616_hdmi_read(hdmi, 0xA4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2032) v_front_porch = ((it6616_hdmi_read(hdmi, 0xA8) & 0xF0) << 4) + it6616_hdmi_read(hdmi, 0xA7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2033) v_sync_w = ((it6616_hdmi_read(hdmi, 0xA8) & 0x01) << 8) + it6616_hdmi_read(hdmi, 0xA6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2034)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2035) h_sync_pol = (it6616_hdmi_read(hdmi, 0xAA) & BIT(5)) >> 5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2036) v_sync_pol = (it6616_hdmi_read(hdmi, 0xAA) & BIT(6)) >> 6;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2037)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2038) it6616->vinfo.h_active = h_active;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2039) it6616->vinfo.h_total = h_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2040) it6616->vinfo.h_front_porch = h_front_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2041) it6616->vinfo.h_sync_w = h_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2042) it6616->vinfo.h_back_porch = (h_total - h_active - h_front_porch - h_sync_w);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2043) it6616->vinfo.v_active = v_active;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2044) it6616->vinfo.v_total = v_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2045) it6616->vinfo.v_front_porch = v_front_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2046) it6616->vinfo.v_sync_w = v_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2047) it6616->vinfo.v_back_porch = v_total - v_active - v_front_porch - v_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2048) it6616->vinfo.interlaced = (interlaced) & 0x01;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2049) it6616->vinfo.v_sync_pol = (v_sync_pol) & 0x01;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2050) it6616->vinfo.h_sync_pol = (h_sync_pol) & 0x01;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2051)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2052) frame_rate = (u32)(it6616->vinfo.pclk) * 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2053) frame_rate /= it6616->vinfo.h_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2054) frame_rate /= it6616->vinfo.v_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2055) it6616->vinfo.frame_rate = frame_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2056)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2057) if (it6616->avi_if.colorspace == HDMI_COLORSPACE_YUV420) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2058) dev_dbg(dev, "HActive = %d\n", it6616->vinfo.h_active*2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2059) dev_dbg(dev, "HTotal = %d\n", it6616->vinfo.h_total*2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2060) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2061) dev_dbg(dev, "HActive = %d\n", it6616->vinfo.h_active);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2062) dev_dbg(dev, "HTotal = %d\n", it6616->vinfo.h_total);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2063) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2064)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2065) dev_dbg(dev, "VActive = %d\n", it6616->vinfo.v_active);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2066) dev_dbg(dev, "VTotal = %d\n", it6616->vinfo.v_total);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2067)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2068) if (it6616->avi_if.colorspace == HDMI_COLORSPACE_YUV420) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2069) dev_dbg(dev, "HFrontPorch = %d\n", it6616->vinfo.h_front_porch*2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2070) dev_dbg(dev, "HSyncWidth = %d\n", it6616->vinfo.h_sync_w*2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2071) dev_dbg(dev, "HBackPorch = %d\n", it6616->vinfo.h_back_porch*2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2072) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2073) dev_dbg(dev, "HFrontPorch = %d\n", it6616->vinfo.h_front_porch);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2074) dev_dbg(dev, "HSyncWidth = %d\n", it6616->vinfo.h_sync_w);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2075) dev_dbg(dev, "HBackPorch = %d\n", it6616->vinfo.h_back_porch);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2076) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2077)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2078) dev_dbg(dev, "VFrontPorch = %d\n", it6616->vinfo.v_front_porch);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2079) dev_dbg(dev, "VSyncWidth = %d\n", it6616->vinfo.v_sync_w);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2080) dev_dbg(dev, "VBackPorch = %d\n", it6616->vinfo.v_back_porch);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2081) dev_dbg(dev, "FrameRate = %u\n", it6616->vinfo.frame_rate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2082)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2083) if (it6616->vinfo.interlaced)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2084) dev_dbg(dev, "ScanMode = InterLaced\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2085) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2086) dev_dbg(dev, "ScanMode = Progressive\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2087)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2088) if (it6616->vinfo.v_sync_pol)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2089) dev_dbg(dev, "VSyncPol = Positive\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2090) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2091) dev_dbg(dev, "VSyncPol = Negative\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2092)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2093) if (it6616->vinfo.h_sync_pol)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2094) dev_dbg(dev, "HSyncPol = Positive\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2095) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2096) dev_dbg(dev, "HSyncPol = Negative");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2097) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2098)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2099) static void it6616_hdmi_hpd_output(struct it6616 *it6616, u8 hpd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2100) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2101) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2102)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2103) it6616_hdmi_chgbank(hdmi, 3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2104)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2105) if (hpd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2106) it6616_hdmi_set(hdmi, 0xAB, 0xC0, 0xC0); // SET PORT0 HPD HIGH
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2107) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2108) it6616_hdmi_set(hdmi, 0xAB, 0xC0, 0x40); // SET PORT0 HPD LOW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2109)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2110) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2111) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2112)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2113) static void it6616_hdmi_hdcp_reset(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2114) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2115) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2116)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2117) it6616_hdmi_set(hdmi, 0x23, 0x02, 0x02);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2118) it6616_hdmi_set(hdmi, 0x23, 0x02, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2119) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2120)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2121) static bool it6616_hdmi_get_hdcp_status(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2122) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2123) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2124)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2125) return it6616_hdmi_read(hdmi, 0xCF) & BIT(5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2126) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2127)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2128) static bool it6616_get_hdcp_status(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2129) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2130) bool hdcp_status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2131)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2132) hdcp_status = it6616_hdmi_get_hdcp_status(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2133)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2134) return hdcp_status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2135) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2136)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2137) static enum av_mute_state it6616_hdmi_rx_get_av_mute_state(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2138) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2139) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2140) bool av_mute_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2141)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2142) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2143) av_mute_state = !!(it6616_hdmi_read(hdmi, 0xAA) & BIT(3));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2145) return av_mute_state ? AV_MUTE_ON : AV_MUTE_OFF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2146) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2147)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2148) static void it6616_hdmi_rx_set_av_mute(struct it6616 *it6616, enum av_mute_state mute_state)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2149) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2150) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2151)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2152) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2154) switch (mute_state) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2155) case AV_MUTE_OFF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2156) it6616_hdmi_set(hdmi, 0x4F, BIT(5), 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2157)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2158) if (!it6616->mipi_tx_enable_mipi_output) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2159) it6616_hdmi_rx_get_video_info(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2160) it6616_mipi_tx_get_support_format(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2161) it6616_enable_mipi(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2162) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2163) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2164) case AV_MUTE_ON:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2165) it6616_hdmi_set(hdmi, 0x4F, BIT(5), BIT(5));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2166) it6616_disable_mipi(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2167) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2168) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2169) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2170) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2171) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2172)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2173) static void it6616_hdmi_update_rs(struct it6616 *it6616, u8 level)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2174) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2175) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2176) u8 rs_val = level;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2177)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2178) it6616_hdmi_chgbank(hdmi, 3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2179) it6616_hdmi_set(hdmi, 0x26, 0x20, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2180) it6616_hdmi_write(hdmi, 0x27, rs_val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2181) it6616_hdmi_write(hdmi, 0x28, rs_val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2182) it6616_hdmi_write(hdmi, 0x29, rs_val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2183) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2184) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2185)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2186) static void it6616_mipi_tx_calc_rclk(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2187) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2188) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2189) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2190) unsigned long sum = 0, ul100msCNT = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2191) u8 i, retry = 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2192)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2193) for (i = 0; i < retry; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2194) it6616_mipi_tx_set_bits(mipi, 0xE0, 0x80, 0x80); // Enable RCLK 100ms count
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2195) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2196) it6616_mipi_tx_set_bits(mipi, 0xE0, 0x80, 0x00); // Disable RCLK 100ms count
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2197)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2198) ul100msCNT = it6616_mipi_tx_read(mipi, 0xE3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2199) ul100msCNT = ((ul100msCNT << 8) | (it6616_mipi_tx_read(mipi, 0xE2)));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2200) ul100msCNT = ((ul100msCNT << 8) | (it6616_mipi_tx_read(mipi, 0xE1)));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2201)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2202) sum += ul100msCNT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2203) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2204) sum /= retry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2205)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2206) it6616->tx_rclk = sum / TIMER_100MS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2207) dev_dbg(dev, "mipi rclk = %d.%d MHz", it6616->tx_rclk / 1000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2208) it6616->tx_rclk % 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2209) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2210)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2211) static void it6616_mipi_tx_calc_mclk(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2212) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2213) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2214) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2215) unsigned long sum = 0, ulCNT, tx_mclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2216) u8 i, retry = 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2217)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2218) for (i = 0; i < retry; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2219) it6616_mipi_tx_set_bits(mipi, 0xE7, 0x80, 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2220) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2221) it6616_mipi_tx_set_bits(mipi, 0xE7, 0x80, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2222)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2223) ulCNT = it6616_mipi_tx_read(mipi, 0xE7) & 0x0F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2224) ulCNT = (it6616_mipi_tx_read(mipi, 0xE6) | (ulCNT << 8));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2226) sum += ulCNT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2227) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2229) sum /= retry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2230)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2231) //MCLK = 13500*2048/sum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2232) //MCLK = 27000*2048/sum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2233) tx_mclk = it6616->tx_rclk * 2048 / sum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2234) dev_dbg(dev, "mipi mclk = %lu.%lu MHz", tx_mclk / 1000, tx_mclk % 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2235) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2236)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2237) static void it6616_mipi_tx_calc_pclk(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2238) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2239) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2240) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2241) unsigned long sum = 0, ulCNT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2242) u8 i, retry = 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2243)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2244) for (i = 0; i < retry; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2245) it6616_mipi_tx_set_bits(mipi, 0xE5, 0x80, 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2246) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2247) it6616_mipi_tx_set_bits(mipi, 0xE5, 0x80, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2248)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2249) ulCNT = it6616_mipi_tx_read(mipi, 0xE5) & 0x0F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2250) ulCNT = it6616_mipi_tx_read(mipi, 0xE4) + (ulCNT << 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2251)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2252) sum += ulCNT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2253) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2254)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2255) sum /= retry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2256)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2257) //PCLK = 13500*2048/sum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2258) //PCLK = 27000*2048/sum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2259) it6616->tx_pclk = it6616->tx_rclk * 2048 / sum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2260) dev_dbg(dev, "mipi pclk = %u.%u MHz", it6616->tx_pclk / 1000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2261) it6616->tx_pclk % 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2262) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2263)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2264) static u32 it6616_hdmi_rx_calc_rclk(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2265) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2266) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2267) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2268) u32 rddata, rclk, sum = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2269) int i, retry = 5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2270) int t1usint;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2271) int t1usflt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2272)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2273) for (i = 0; i < retry; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2274) it6616_hdmi_set(hdmi, 0x58, 0x80, 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2275) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2276) it6616_hdmi_set(hdmi, 0x58, 0x80, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2277)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2278) rddata = it6616_hdmi_read(hdmi, 0x59);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2279) rddata += (it6616_hdmi_read(hdmi, 0x5A) << 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2280) rddata += (it6616_hdmi_read(hdmi, 0x5B) << 16);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2281)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2282) sum += rddata;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2283) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2284)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2285) sum /= retry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2286) rclk = sum / TIMER_100MS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2287)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2288) dev_dbg(dev, "RCLK=%u KHz\n", rclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2289)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2290) t1usint = rclk / 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2291) t1usflt = (rclk / 1000 - t1usint) * 256;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2292) it6616_hdmi_set(hdmi, 0x1E, 0x3F, t1usint & 0x3F);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2293) it6616_hdmi_write(hdmi, 0x1F, t1usflt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2294)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2295) it6616->rclk = rclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2296)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2297) return rclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2298) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2299)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2300) static u32 it6616_hdmi_rx_calc_pclk(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2301) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2302) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2303) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2304) u32 retry = 5, rddata, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2305) u32 pclk, sump = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2306)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2307) __recal:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2308) for (i = 0; i < retry; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2309) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2310) it6616_hdmi_set(hdmi, 0x9A, BIT(7), 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2311) rddata = ((u32)(it6616_hdmi_read(hdmi, 0x9A) & 0x03) << 8) +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2312) it6616_hdmi_read(hdmi, 0x99);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2313) it6616_hdmi_set(hdmi, 0x9A, BIT(7), BIT(7));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2314) sump += rddata;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2315) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2316)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2317) sump /= retry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2318)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2319) if (sump) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2320) pclk = it6616->rclk * 512 / sump; // 512=2*256 because of 1T 2 pixel
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2321) dev_dbg(dev, "PCLK = %u.%03u MHz", pclk / 1000, pclk % 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2322) it6616->vinfo.pclk = pclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2323) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2324) dev_err(dev, "%s: sump == 0", __func__);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2325) goto __recal;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2326) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2327)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2328) return pclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2329) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2330)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2331) static void it6616_hdmi_rx_calc_tmds_clk(struct it6616 *it6616, u8 count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2332) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2333) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2334) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2335) u32 sumt = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2336) u8 rddata = 0, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2337)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2338) for (i = 0; i < count; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2339) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2340) rddata = it6616_hdmi_read(hdmi, 0x48) + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2341) sumt += rddata;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2342) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2343)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2344) if (sumt) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2345) rddata = it6616_hdmi_read(hdmi, 0x43) & 0xE0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2346)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2347) if (rddata & BIT(7))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2348) it6616->vinfo.TMDSCLK = (it6616->rclk * (u32)1024 * i) / sumt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2349) else if (rddata & BIT(6))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2350) it6616->vinfo.TMDSCLK = (it6616->rclk * (u32)512 * i) / sumt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2351) else if (rddata & BIT(5))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2352) it6616->vinfo.TMDSCLK = (it6616->rclk * (u32)256 * i) / sumt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2353) if (rddata == 0x00)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2354) it6616->vinfo.TMDSCLK = (it6616->rclk * (u32)128 * i) / sumt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2355)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2356) dev_dbg(dev, "TMDSCLK = %u.%03uMHz\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2357) it6616->vinfo.TMDSCLK / 1000, it6616->vinfo.TMDSCLK % 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2358) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2359) dev_err(dev, "%s - sumt==0\n", __func__);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2360) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2361) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2362)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2363) static void it6616_hdmi_receive_avi_infoframe_log(struct it6616 *it6616, u8 *buffer, size_t length)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2364) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2365) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2366) u8 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2367)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2368) dev_dbg(dev, "avi infoframe:");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2369) for (i = 0; i < length; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2370) dev_err(dev, "0x%02x", buffer[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2371) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2372)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2373) static int it6616_hdmi_update_avi_infoframe(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2374) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2375) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2376) struct hdmi_avi_infoframe *frame = &it6616->avi_if;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2377) u8 avi_packet[20] = { 0 };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2378)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2379) avi_packet[0] = HDMI_INFOFRAME_TYPE_AVI;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2380) it6616_hdmi_chgbank(hdmi, 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2381) avi_packet[1] = it6616_hdmi_read(hdmi, REG_RX_AVI_HB1);// version
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2382) avi_packet[2] = it6616_hdmi_read(hdmi, REG_RX_AVI_HB2);// version
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2383) regmap_bulk_read(hdmi, REG_RX_AVI_DB0, &avi_packet[3], 16);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2384) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2385)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2386) it6616_hdmi_receive_avi_infoframe_log(it6616, avi_packet, ARRAY_SIZE(avi_packet));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2387)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2388) return hdmi_infoframe_unpack((union hdmi_infoframe *)frame, avi_packet, sizeof(avi_packet));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2389) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2390)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2391) static void it6616_hdmi_rx_setup_csc(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2392) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2393) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2394) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2395) enum hdmi_colorspace color_in;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2396) enum hdmi_colorspace color_out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2397) enum csc_select csc_select;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2398) enum csc_matrix_type csc_matrix_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2399) u8 reg6b = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2400) u8 reg6e = ((HDMI_RX_AUTO_CSC_SELECT << 7) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2401) (HDMI_RX_QUANT_4LB << 6) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2402) (HDMI_RX_CRCB_LIMIT << 5) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2403) (HDMI_RX_COLOR_CLIP << 4) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2404) (HDMI_RX_ENABLE_DITHER_FCNT_FUNCTION << 2) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2405) (HDMI_RX_ENABLE_DITHER_FUNCTION << 1) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2406) HDMI_RX_ENABLE_COLOR_UP_DN_FILTER);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2407)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2408) color_in = it6616->avi_if.colorspace;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2409) color_out = it6616_hdmi_get_output_color_space(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2410)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2411) if (color_in == HDMI_COLORSPACE_RGB && color_out != HDMI_COLORSPACE_RGB)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2412) csc_select = CSC_RGB2YUV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2413) else if (color_in != HDMI_COLORSPACE_RGB && color_out == HDMI_COLORSPACE_RGB)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2414) csc_select = CSC_YUV2RGB;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2415) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2416) csc_select = CSC_BYPASS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2417)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2418) switch (csc_select) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2419) case CSC_RGB2YUV:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2420) dev_info(dev, "csc rgb2yuv");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2421) if (it6616->avi_if.colorimetry == HDMI_COLORIMETRY_ITU_709) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2422) if (it6616->avi_if.quantization_range == HDMI_QUANTIZATION_RANGE_LIMITED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2423) csc_matrix_type = CSCMtx_RGB2YUV_ITU709_16_235;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2424) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2425) csc_matrix_type = CSCMtx_RGB2YUV_ITU709_00_255;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2426) } else {/* HDMI_COLORIMETRY_ITU_601 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2427) if (it6616->avi_if.quantization_range == HDMI_QUANTIZATION_RANGE_LIMITED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2428) csc_matrix_type = CSCMtx_RGB2YUV_ITU601_16_235;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2429) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2430) csc_matrix_type = CSCMtx_RGB2YUV_ITU601_00_255;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2431) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2432) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2433)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2434) case CSC_YUV2RGB:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2435) dev_info(dev, "csc yuv2rgb");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2436)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2437) if (it6616->avi_if.colorimetry == HDMI_COLORIMETRY_ITU_709)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2438) // when 709 format always to RGB full range
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2439) csc_matrix_type = CSCMtx_YUV2RGB_ITU709_00_255;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2440) else if (it6616->avi_if.colorimetry == HDMI_COLORIMETRY_EXTENDED &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2441) (it6616->avi_if.extended_colorimetry == 0x05 ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2442) it6616->avi_if.extended_colorimetry == 0x06))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2443) // this Matrix is BT2020 YUV to BT2020 RGB, not normal limit/full range RGB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2444) csc_matrix_type = CSCMtx_YUV2RGB_BT2020_00_255; // for BT.2020 CSC
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2445) else /* Colormetry_ITU601 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2446) csc_matrix_type = CSCMtx_YUV2RGB_ITU601_00_255;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2447) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2448)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2449) case CSC_BYPASS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2450) dev_info(dev, "csc byass");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2451) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2452) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2453)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2454) if (csc_select != CSC_BYPASS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2455) it6616_hdmi_chgbank(hdmi, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2456) regmap_bulk_write(hdmi, 0x70, (u8 *)csc_matrix[csc_matrix_type],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2457) sizeof(csc_matrix[0]));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2458) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2459) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2460) it6616_hdmi_set(hdmi, 0x6E, 0xF7, reg6e);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2461)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2462) it6616_hdmi_set(hdmi, 0x6C, 0x03, csc_select);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2463)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2464) switch (color_in) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2465) case HDMI_COLORSPACE_YUV422:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2466) reg6b = 1 << 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2467) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2468) case HDMI_COLORSPACE_YUV444:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2469) reg6b = 2 << 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2470) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2471) case HDMI_COLORSPACE_YUV420:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2472) reg6b = 3 << 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2473) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2474) case HDMI_COLORSPACE_RGB:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2475) reg6b = 0 << 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2476) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2477) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2478) dev_err(dev, "## unknown input color space %x\n", color_in);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2479) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2480) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2481)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2482) switch (color_out) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2483) case HDMI_COLORSPACE_YUV422:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2484) reg6b |= 1 << 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2485) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2486) case HDMI_COLORSPACE_YUV444:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2487) reg6b |= 2 << 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2488) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2489) case HDMI_COLORSPACE_YUV420:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2490) reg6b |= 3 << 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2491) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2492) case HDMI_COLORSPACE_RGB:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2493) reg6b |= 0 << 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2494) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2495) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2496) dev_err(dev, "## unknown output color space %x\n", color_out);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2497) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2498) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2499)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2500) if (it6616->mipi.bus_type == MIPI_CSI) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2501) switch (it6616->mipi.data_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2502) case CSI_RGB10b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2503) reg6b |= 1 << 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2504) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2505) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2506) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2507) switch (it6616->mipi.data_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2508) case DSI_RGB_36b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2509) reg6b |= 2 << 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2510) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2511) case DSI_RGB_30b:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2512) reg6b |= 1 << 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2513) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2514) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2515) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2516)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2517) it6616_hdmi_set(hdmi, 0x6B, 0x3F, reg6b);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2518) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2519)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2520) static void it6616_hdmi_rx_reset_audio_logic(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2521) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2522) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2523) u8 temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2524)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2525) it6616_hdmi_set(hdmi, 0x22, BIT(1), BIT(1)); // audio reset
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2526) msleep(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2527) it6616_hdmi_set(hdmi, 0x22, BIT(1), 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2528)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2529) // RegFS_Set[5:0] : Software set sampling frequency R/W
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2530) temp = it6616_hdmi_read(hdmi, 0x8A);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2531) it6616_hdmi_write(hdmi, 0x8A, temp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2532) it6616_hdmi_write(hdmi, 0x8A, temp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2533) it6616_hdmi_write(hdmi, 0x8A, temp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2534) it6616_hdmi_write(hdmi, 0x8A, temp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2535) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2536)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2537) static void it6616_hdmi_rx_audio_setup_i2s_justified(struct it6616 *it6616, u8 i2s_justified)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2538) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2539) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2540)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2541) i2s_justified = (i2s_justified == FROM_CONFIG) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2542) it6616->audio_i2s_justified : i2s_justified;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2543) it6616_hdmi_set(hdmi, 0x0F, 0x03, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2544) it6616_hdmi_set(hdmi, 0x82, 0x03, i2s_justified);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2545) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2546)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2547) static void it6616_hdmi_tx_audio_setup(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2548) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2549) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2550) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2551) u32 sum = 0, cts_128;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2552)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2553) // RegForce_CTSMode : need to set to 1 for get the cts in the PKT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2554) // 0 repersent nothing (HW using)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2555) // so set to 1 to get cts in the REG2C1/2C2/2C0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2556) it6616_hdmi_set(hdmi, 0x86, BIT(0), BIT(0));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2557) it6616_hdmi_rx_audio_setup_i2s_justified(it6616, FROM_CONFIG);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2558) it6616_hdmi_chgbank(hdmi, 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2559) it6616->ainfo.n = ((u32)it6616_hdmi_read(hdmi, 0xBE) << 12) +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2560) ((u32)it6616_hdmi_read(hdmi, 0xBF) << 4) +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2561) ((u32)it6616_hdmi_read(hdmi, 0xC0) & 0x0F);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2562) it6616->ainfo.cts = it6616_hdmi_read(hdmi, 0xC0) >> 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2563) it6616->ainfo.cts |= ((u32)it6616_hdmi_read(hdmi, 0xC1)) << 12;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2564) it6616->ainfo.cts |= ((u32)it6616_hdmi_read(hdmi, 0xC2)) << 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2565) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2566)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2567) if (it6616->ainfo.cts == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2568) dev_info(dev, "WARNING:cts = %u", it6616->ainfo.cts);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2569) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2570) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2571)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2572) // in the hdmi2.0 page 84, need bit 24, 25, 26, 27, 30, 31
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2573) // Audio_CH_Status : Audio Channel status decoder value[31:24]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2574) // and bit[24:27] = Audio Sampling Rate
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2575) it6616->ainfo.channel_status = ((it6616_hdmi_read(hdmi, 0xB5) & 0xC0) >> 2) +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2576) (it6616_hdmi_read(hdmi, 0xB5) & 0x0F);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2577) cts_128 = 128 * it6616->ainfo.cts;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2578) sum = it6616->ainfo.n * it6616->vinfo.TMDSCLK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2579) it6616->ainfo.sample_freq = sum / cts_128;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2581) dev_info(dev, "n = %u cts = %u\n", it6616->ainfo.n, it6616->ainfo.cts);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2582) dev_info(dev, "tmds clock = %d kHz\n", it6616->vinfo.TMDSCLK);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2583) dev_info(dev, "Audio_CH_Status[24:27 - 30:31][bit0~bit5] = 0x%02x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2584) it6616->ainfo.channel_status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2585) dev_info(dev, "sw clac sampling frequency = %d.%d kHz\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2586) it6616->ainfo.sample_freq, (sum % cts_128) * 100 / cts_128);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2587)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2588) if (it6616->ainfo.sample_freq > 25 && it6616->ainfo.sample_freq <= 38)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2589) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_32K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2590) else if (it6616->ainfo.sample_freq > 38 && it6616->ainfo.sample_freq <= 45)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2591) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_44P1K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2592) else if (it6616->ainfo.sample_freq > 45 && it6616->ainfo.sample_freq <= 58)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2593) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_48K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2594) else if (it6616->ainfo.sample_freq > 58 && it6616->ainfo.sample_freq <= 78)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2595) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_64K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2596) else if (it6616->ainfo.sample_freq > 78 && it6616->ainfo.sample_freq <= 91)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2597) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_88P2K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2598) else if (it6616->ainfo.sample_freq > 91 && it6616->ainfo.sample_freq <= 106)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2599) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_96K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2600) else if (it6616->ainfo.sample_freq > 106 && it6616->ainfo.sample_freq <= 166)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2601) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_128K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2602) else if (it6616->ainfo.sample_freq > 166 && it6616->ainfo.sample_freq <= 182)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2603) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_176P4K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2604) else if (it6616->ainfo.sample_freq > 182 && it6616->ainfo.sample_freq <= 202)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2605) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_192K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2606) else if (it6616->ainfo.sample_freq > 224 && it6616->ainfo.sample_freq <= 320)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2607) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_256K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2608) else if (it6616->ainfo.sample_freq > 320 && it6616->ainfo.sample_freq <= 448)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2609) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_384K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2610) else if (it6616->ainfo.sample_freq > 448 && it6616->ainfo.sample_freq <= 638)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2611) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_512K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2612) else if (it6616->ainfo.sample_freq > 638 && it6616->ainfo.sample_freq <= 894)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2613) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_768K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2614) else if (it6616->ainfo.sample_freq > 894 && it6616->ainfo.sample_freq <= 1324)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2615) it6616->ainfo.force_sample_freq = AUDIO_SAMPLING_1024K;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2617) dev_info(dev, "Sampling_Frequency value 0x%02x", it6616->ainfo.force_sample_freq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2618)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2619) if (it6616->ainfo.channel_status == it6616->ainfo.force_sample_freq) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2620) dev_dbg(dev, "channel_status == force_sample_freq\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2621) if (it6616_hdmi_read(hdmi, 0x81) & BIT(6)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2622) // RegForce_FS : 0: Disable Force Audio FS mode
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2623) it6616_hdmi_set(hdmi, 0x81, BIT(6), 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2624) it6616_hdmi_rx_reset_audio_logic(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2625) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2626) it6616->audio_sampling_freq_error_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2627) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2628) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2629)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2630) it6616->audio_sampling_freq_error_count++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2631) dev_dbg(dev, "it6616->audio_sampling_freq_error_count=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2632) (int) it6616->audio_sampling_freq_error_count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2633)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2634) /* exceed max error count , enable Force Sampling Mode */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2635) if (it6616->audio_sampling_freq_error_count > MAX_AUDIO_SAMPLING_FREQ_ERROR_COUNT) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2636) it6616_hdmi_set(hdmi, 0x81, BIT(6), BIT(6)); // RegForce_FS : Force Audio FS mode
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2637) // RegFS_Set[5:0] : Software set sampling frequency
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2638) it6616_hdmi_set(hdmi, 0x8A, 0x3F, it6616->ainfo.force_sample_freq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2639)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2640) #if defined(Enable_Audio_Compatibility) && (Enable_Audio_Compatibility == 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2641) if (it6616->ainfo.sample_freq <= 182) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2642) it6616_hdmi_set(hdmi, 0x89, 0x0C, 0x04);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2643) it6616_hdmi_set(hdmi, 0x86, 0x0C, 0x0C);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2644) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2645) it6616_hdmi_set(hdmi, 0x89, 0x0C, 0x0C);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2646) it6616_hdmi_set(hdmi, 0x86, 0x0C, 0x04);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2647) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2648) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2649) it6616->audio_sampling_freq_error_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2650) it6616_hdmi_rx_reset_audio_logic(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2651) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2652) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2653)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2654) static void it6616_hdmi_tx_audio_output_enable(struct it6616 *it6616, u8 output_interface)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2655) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2656) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2657) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2658)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2659) it6616_hdmi_chgbank(hdmi, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2660)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2661) switch (output_interface) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2662) case AUDIO_OFF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2663) dev_info(dev, "audio off");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2664) it6616_hdmi_write(hdmi, 0xC7, 0x7F); // SPDIF/I2S tri-state on
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2665) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2666)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2667) case AUDIO_I2S:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2668) case AUDIO_SPDIF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2669) dev_info(dev, "enable audio output");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2670) it6616_hdmi_write(hdmi, 0xC7, 0x00); // SPDIF/I2S tri-state off
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2671) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2672) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2673)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2674) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2675) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2676)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2677) static void it6616_hdmi_audio_mute_clear(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2678) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2679) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2680)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2681) it6616_hdmi_set(hdmi, 0x8C, BIT(4), BIT(4)); // set RegHWMuteClr
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2682) it6616_hdmi_set(hdmi, 0x8C, BIT(4), 0x00); // clear RegHWMuteClr for clear H/W Mute
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2683) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2684)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2685)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2686) static void it6616_hdmi_rx_audio_process(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2687) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2688) it6616_hdmi_tx_audio_output_enable(it6616, AUDIO_OFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2689) it6616_hdmi_rx_reset_audio_logic(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2690) it6616_hdmi_tx_audio_setup(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2691) it6616_hdmi_audio_mute_clear(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2692) it6616_hdmi_tx_audio_output_enable(it6616, it6616->audio_interface);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2693) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2694)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2695) static void it6616_hdmi_initial(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2696) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2697) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2698) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2699)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2700) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2701) it6616_hdim_write_table(hdmi, it6616_hdmi_init_table);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2702)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2703) it6616_hdmi_update_rs(it6616, DEFAULT_RS_LEVEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2704) it6616_hdmi_set(hdmi, 0x67, BIT(7), it6616->hdmi_rx_disable_pixel_repeat << 7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2705) it6616_hdmi_set(hdmi, 0x69, BIT(6) | BIT(5),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2706) it6616->hdmi_rx_video_stable_condition << 5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2707) dev_dbg(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2708) "set hdmi rx video stable condition, reg0x69[6:5], 0x%02x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2709) it6616_hdmi_read(hdmi, 0x69));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2710) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2711)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2712) static void it6616_hdmi_irq_color_depth(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2713) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2714) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2715) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2716) u8 input_color_depth;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2717)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2718) input_color_depth = (it6616_hdmi_read(hdmi, 0x98) >> 4) & 0x0F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2719) dev_dbg(dev, "input color depth = %d bits\n", input_color_depth * 6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2720) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2721)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2722) static void it6616_hdmi_irq_new_avi_infoframe(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2723) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2724) struct hdmi_avi_infoframe *avi_new;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2725) struct hdmi_avi_infoframe *avi_prev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2726)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2727) if (it6616_hdmi_update_avi_infoframe(it6616) == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2728) avi_new = &it6616->avi_if;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2729) avi_prev = &it6616->avi_if_prev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2730) hdmi_infoframe_log(KERN_INFO, &it6616->hdmi_i2c->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2731) (union hdmi_infoframe *)avi_new);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2732)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2733) if (avi_prev->video_code != avi_new->video_code)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2734) avi_prev->video_code = avi_new->video_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2735) if (avi_prev->colorspace != avi_new->colorspace)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2736) avi_prev->colorspace = avi_new->colorspace;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2737) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2738) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2739)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2740) static void it6616_hdmi_hpd_trun_on(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2741) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2742) it6616_hdmi_edid_ram_enable(it6616, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2743) it6616_hdmi_video_reset(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2744) it6616_hdmi_rx_reset_audio_logic(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2745) it6616_hdmi_hpd_output(it6616, true);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2746) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2747)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2748) static void it6616_hdmi_hpd_trun_off(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2749) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2750) it6616_hdmi_hpd_output(it6616, false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2751) it6616_hdmi_edid_ram_enable(it6616, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2752) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2753)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2754) static void it6616_mipitx_irq(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2755) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2756) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2757) struct device *dev = &it6616->mipi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2758) u8 reg09h, reg0ah, reg0bh;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2759)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2760) reg09h = it6616_mipi_tx_read(mipi, 0x09);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2761) reg0ah = it6616_mipi_tx_read(mipi, 0x0A);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2762) reg0bh = it6616_mipi_tx_read(mipi, 0x0B);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2763)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2764) it6616_mipi_tx_write(mipi, 0x0A, reg0ah);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2765) it6616_mipi_tx_write(mipi, 0x0B, reg0bh);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2766)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2767) if (reg0bh & 0x10) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2768) it6616->mipi_tx_video_stable = it6616_mipi_tx_get_video_stable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2769) dev_info(dev, "mipi tx Video Stable Change ...");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2770) dev_info(dev, "mipi tx reg09 = 0x%02x, video %sstable",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2771) reg09h, it6616->mipi_tx_video_stable ? "" : "un");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2772)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2773) if (it6616->mipi_tx_video_stable) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2774) it6616_mipi_tx_calc_rclk(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2775) it6616_mipi_tx_calc_mclk(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2776) it6616_mipi_tx_calc_pclk(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2777) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2778) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2779)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2780) if (reg0ah & 0x70) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2781) if (reg0ah & 0x20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2782) dev_err(dev, "Mipi Byte mismatch Err!!!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2783) if (reg0ah & 0x40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2784) dev_err(dev, "mipi P2M FIFO Err!!!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2785) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2786) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2787)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2788) static void it6616_hdmi_irq(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2789) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2790) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2791) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2792)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2793) u8 reg05h, reg06h, Reg08h, Reg09h;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2794) u8 Reg10h, Reg11h, Reg12h;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2795) u8 Reg13h, Reg14h, Reg15h;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2796) u8 Reg1Ah, Reg1Bh;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2797)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2798) reg05h = it6616_hdmi_read(hdmi, 0x05);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2799) it6616_hdmi_write(hdmi, 0x05, reg05h);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2800) reg06h = it6616_hdmi_read(hdmi, 0x06);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2801) it6616_hdmi_write(hdmi, 0x06, reg06h);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2802) Reg08h = it6616_hdmi_read(hdmi, 0x08);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2803) it6616_hdmi_write(hdmi, 0x08, Reg08h);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2804) Reg09h = it6616_hdmi_read(hdmi, 0x09);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2805) it6616_hdmi_write(hdmi, 0x09, Reg09h);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2806)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2807) Reg10h = it6616_hdmi_read(hdmi, 0x10);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2808) it6616_hdmi_write(hdmi, 0x10, Reg10h);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2809)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2810) Reg11h = it6616_hdmi_read(hdmi, 0x11);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2811) it6616_hdmi_write(hdmi, 0x11, Reg11h);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2812)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2813) Reg12h = it6616_hdmi_read(hdmi, 0x12);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2814) it6616_hdmi_write(hdmi, 0x12, Reg12h & 0x7F);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2815)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2816) Reg13h = it6616_hdmi_read(hdmi, 0x13);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2817) Reg14h = it6616_hdmi_read(hdmi, 0x14);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2818) Reg15h = it6616_hdmi_read(hdmi, 0x15);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2819)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2820) if (reg05h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2821) if (reg05h & 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2822) dev_info(dev, "# hdmi mode chg #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2823) if (reg05h & 0x20) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2824) dev_err(dev, "# ECC Error #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2825) it6616_hdmi_hdcp_reset(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2826) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2827) if (reg05h & 0x40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2828) dev_err(dev, "# Deskew Error #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2829) if (reg05h & 0x80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2830) dev_err(dev, "# H2VSkew Fail #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2831) if (reg05h & 0x04) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2832) dev_info(dev, "# Input Clock Change Detect #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2833) if (it6616_hdmi_is_clock_stable(it6616))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2834) dev_info(dev, "# Clock Stable #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2835) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2836) dev_err(dev, "# Clock NOT Stable #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2837) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2838)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2839) if (reg05h & 0x02)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2840) dev_info(dev, "# Rx CKOn Detect #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2841)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2842) if (reg05h & 0x01) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2843) dev_info(dev, "# 5V state change INT #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2844) it6616_hdmi_hdcp_reset(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2845) if (it6616_hdmi_is_5v_on(it6616))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2846) it6616_hdmi_hpd_trun_on(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2847) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2848) it6616_hdmi_hpd_trun_off(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2849) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2850) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2851)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2852) if (reg06h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2853) if (reg06h & 0x80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2854) dev_err(dev, "# FSM Error #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2855) if (reg06h & 0x40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2856) dev_err(dev, "# CH2 Symbol lock Rst #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2857) if (reg06h & 0x20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2858) dev_err(dev, "# CH1 Symbol lock Rst #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2859) if (reg06h & 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2860) dev_err(dev, "# CH0 Symbol lock Rst #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2861) if (reg06h & 0x08)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2862) dev_err(dev, "# CH2 CDR FIFO Aut0-Rst #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2863) if (reg06h & 0x04)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2864) dev_err(dev, "# CH1 CDR FIFO Aut0-Rst #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2865) if (reg06h & 0x02)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2866) dev_err(dev, "# CH0 CDR FIFO Aut0-Rst #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2867) if (reg06h & 0x01)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2868) dev_info(dev, "# Symbol Lock State Change # ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2869) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2870)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2871) if (Reg09h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2872) if (Reg09h & 0x01)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2873) dev_info(dev, "# HDCP Authentication Start #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2874) if (Reg09h & 0x02) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2875) dev_info(dev, "# HDCP Authentication Done #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2876) it6616->hdmi_rx_hdcp_state = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2877) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2878) if (Reg09h & 0x04) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2879) it6616->hdmi_rx_hdcp_state = it6616_get_hdcp_status(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2880) dev_info(dev, "HDCP Encryption change interrupt!");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2881) dev_info(dev, "HDCP Encryption %s!",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2882) it6616->hdmi_rx_hdcp_state ? "ON" : "OFF");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2883) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2884) if (Reg09h & 0x08) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2885) dev_info(dev, "# HDCP Off #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2886) it6616->hdmi_rx_hdcp_state = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2887) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2888) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2889)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2890) if (Reg12h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2891) if (Reg12h & BIT(7)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2892) Reg1Ah = it6616_hdmi_read(hdmi, 0x1A);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2893) Reg1Bh = it6616_hdmi_read(hdmi, 0x1B) & 0x07;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2894) dev_info(dev, "# Video Parameters Change #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2895) dev_info(dev, "# VidParaChange_Sts=Reg1Bh=0x%02X Reg1Ah=0x%02X\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2896) (int) Reg1Bh, (int) Reg1Ah);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2897) it6616_hdmi_rx_calc_tmds_clk(it6616, 5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2898) it6616_hdmi_rx_calc_pclk(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2899) it6616_hdmi_rx_get_video_info(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2900) // only parameter change need to clear INT here ,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2901) //or register 1A/1B can't be read after clear.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2902) it6616_hdmi_write(hdmi, 0x12, 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2903) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2904)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2905) if (Reg12h & BIT(6))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2906) dev_info(dev, "# 3D audio Valie Change #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2907) if (Reg12h & BIT(5))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2908) dev_info(dev, "# DRM pkt Change #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2909) if (Reg12h & 0x10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2910) dev_info(dev, "# New Audio PKT Received #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2911) if (Reg12h & 0x08)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2912) dev_info(dev, "# New ACP PKT Received #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2913) if (Reg12h & 0x04)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2914) dev_info(dev, "# New SPD PKT Received #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2915) if (Reg12h & 0x02)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2916) dev_info(dev, "# New MPEG InfoFrame Received #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2917) if (Reg12h & 0x01) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2918) dev_info(dev, "# New AVI InfoFrame Received #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2919) it6616_hdmi_irq_new_avi_infoframe(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2920) it6616_hdmi_rx_setup_csc(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2921) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2922) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2923)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2924) if (Reg10h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2925) if (Reg10h & 0x80) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2926) dev_err(dev, "# Audio FIFO Error #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2927) it6616_hdmi_rx_audio_process(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2928) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2929) if (Reg10h & 0x40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2930) dev_info(dev, "# Audio Auto Mute #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2931) // todo: how about on/off flag at the same time ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2932) if ((Reg10h & 0x20)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2933) dev_info(dev, "# PKT Left Mute #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2934) it6616_hdmi_rx_set_av_mute(it6616, AV_MUTE_OFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2935) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2936) if ((Reg10h & 0x10)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2937) dev_info(dev, "# Set Mute PKT Received #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2938) it6616_hdmi_rx_set_av_mute(it6616, AV_MUTE_ON);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2939) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2940) if (Reg10h & 0x08)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2941) dev_info(dev, "# Timer Counter Interrupt #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2942) if (Reg10h & 0x04)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2943) dev_info(dev, "# Video Mode Changed #");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2944) if (Reg10h & 0x02) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2945) it6616->hdmi_rx_video_stable = it6616_hdmi_is_scdt_on(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2946) dev_info(dev, "SCDT %s", it6616->hdmi_rx_video_stable ? "ON" : "OFF");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2947)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2948) if (it6616->hdmi_rx_video_stable) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2949) it6616_hdmi_rx_calc_tmds_clk(it6616, 5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2950) it6616_hdmi_rx_calc_pclk(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2951) it6616_hdmi_rx_get_video_info(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2952) it6616_hdmi_rx_audio_process(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2953) msleep(400);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2954) it6616_mipi_tx_get_support_format(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2955) it6616_enable_mipi(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2956) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2957) it6616_disable_mipi(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2958) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2959) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2960) if (Reg10h & 0x01)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2961) dev_info(dev, "# Video Abnormal Interrupt #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2962) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2963)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2964) if (Reg11h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2965) if (Reg11h & BIT(5))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2966) dev_info(dev, "# No Audio InfoFrame Received #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2967) if (Reg11h & BIT(4))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2968) dev_info(dev, "# No AVI InfoFrame Received #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2969) if (Reg11h & BIT(3)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2970) dev_info(dev, "# CD Detect #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2971) it6616_hdmi_irq_color_depth(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2972) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2973) if (Reg11h & BIT(1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2974) it6616_hdmi_write(hdmi, 0x11, BIT(1));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2975) if (Reg11h & BIT(0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2976) it6616_hdmi_write(hdmi, 0x11, BIT(0));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2977) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2978)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2979) if (Reg13h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2980) if (Reg13h & BIT(0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2981) dev_dbg(dev, "# Port 0 power 5V detect #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2982) if (Reg13h & BIT(1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2983) dev_dbg(dev, "# Port 0 HDMI mode #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2984) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2985) dev_dbg(dev, "# Port 0 DVI mode #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2986) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2987)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2988) if (Reg14h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2989) if (Reg14h & BIT(0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2990) dev_dbg(dev, "# Port 0 IPLL clock is higher than 100MHz #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2991) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2992)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2993) if (Reg15h != 0x00) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2994) if (Reg15h & BIT(6))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2995) dev_dbg(dev, "# Port 0 EDID Idle #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2996) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2997) dev_dbg(dev, "# Port 0 EDID active #\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2998) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2999) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3001) static int it6616_get_chip_id(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3002) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3003) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3004) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3005) u8 chip_id[4] = {0x54, 0x49, 0x16, 0x66};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3006) int i, ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3007)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3008) for (i = 0; i < sizeof(chip_id); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3009) ret = it6616_hdmi_read(hdmi, i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3010)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3011) if (ret != chip_id[i]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3012) dev_err(dev, "not 6616 reg[0x%02x]=0x%02x", i, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3013) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3014) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3015) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3016)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3017) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3018) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3019)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3020) static void it6616_poll_threaded_handler(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3021) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3022) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3023) enum av_mute_state mute_state_config = !!(it6616_hdmi_read(hdmi, 0x4F) & BIT(5));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3024) enum av_mute_state current_mute_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3025)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3026) current_mute_state = it6616_hdmi_rx_get_av_mute_state(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3027)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3028) if (mute_state_config != current_mute_state)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3029) it6616_hdmi_rx_set_av_mute(it6616, current_mute_state);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3030) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3031)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3032) static irqreturn_t it6616_intp_threaded_handler(int unused, void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3033) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3034) struct it6616 *it6616 = (struct it6616 *)data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3035)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3036) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3037)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3038) it6616_hdmi_irq(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3039) it6616_mipitx_irq(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3040)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3041) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3042)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3043) return IRQ_HANDLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3044) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3045)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3046) static int it6616_initial(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3047) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3048) struct device *dev = &it6616->hdmi_i2c->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3049)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3050) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3051)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3052) /* get device id */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3053) if (it6616_get_chip_id(it6616)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3054) dev_err(dev, "can not find it6616");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3055) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3056) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3057)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3058) // init driver variables:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3059) it6616->edid_len = sizeof(default_edid);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3060) memcpy(it6616->edid_data, default_edid, it6616->edid_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3061)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3062) // mipi common settings:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3063) it6616->mipi.bus_type = MIPI_TX_INTERFACE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3064) it6616->mipi.lane_cnt = it6616->csi_lanes_in_use;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3065) it6616->mipi.data_type = MIPI_TX_DATA_TYPE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3066)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3067) it6616->mipi_tx_enable_auto_adjust_lane_count =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3068) MIPI_TX_ENABLE_AUTO_ADJUST_LANE_COUNT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3069) it6616->mipi_tx_enable_h_fire_packet =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3070) MIPI_TX_ENABLE_H_FIRE_PACKET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3071) it6616->mipi_tx_enable_initial_fire_lp_cmd =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3072) MIPI_TX_ENABLE_INITIAL_FIRE_LP_CMD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3073) // hdmi settings:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3074) it6616->rs_level = DEFAULT_RS_LEVEL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3075) it6616->audio_interface = AUDIO_I2S;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3076) it6616->audio_i2s_justified = AUDIO_I2S_JUSTIFIED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3077) it6616->hdmi_rx_disable_pixel_repeat =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3078) HDMI_RX_DISABLE_PIXEL_REPEAT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3079) it6616->hdmi_rx_video_stable_condition =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3080) HDMI_RX_VIDEO_STABLE_CONDITION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3081) it6616->mipi_tx_enable_continuous_clock =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3082) MIPI_TX_ENABLE_CONTINUOUS_CLOCK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3083) it6616->mipi_tx_enable_manual_adjusted_d_phy =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3084) MIPI_TX_ENABLE_MANUAL_ADJUSTED_D_PHY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3085) it6616->hdmi_rx_video_stable = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3086) it6616->mipi_tx_video_stable = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3087) it6616->hdmi_rx_hdcp_state = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3088) it6616->mipi_tx_enable_mipi_output = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3089)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3090) it6616_hdmi_rx_calc_rclk(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3091)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3092) it6616_hdmi_initial(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3093) it6616_hdmi_edid_ram_init(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3094) it6616_mipitx_init_bus_para(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3095) it6616_mipitx_initial(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3096)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3097) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3098)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3099) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3100) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3101)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3102) static __maybe_unused void it6616_set_hpd(struct it6616 *it6616, u8 hpd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3103) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3104) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3105)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3106) if (hpd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3107) it6616_hdmi_hpd_trun_on(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3108) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3109) it6616_hdmi_hpd_trun_off(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3110)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3111) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3112) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3113)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3114) static __maybe_unused void it6616_update_edid_data(struct it6616 *it6616, u8 *edid, int edid_len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3115) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3116) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3117)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3118) memcpy(it6616->edid_data, edid, it6616->edid_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3119) it6616->edid_len = edid_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3120) it6616_hdmi_edid_ram_init(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3121)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3122) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3123) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3124)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3125) static const struct regmap_range it6616_hdmi_volatile_ranges[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3126) { .range_min = 0, .range_max = 0xff },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3127) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3128)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3129) static const struct regmap_access_table it6616_hdmi_volatile_table = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3130) .yes_ranges = it6616_hdmi_volatile_ranges,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3131) .n_yes_ranges = ARRAY_SIZE(it6616_hdmi_volatile_ranges),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3132) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3133)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3134) static const struct regmap_config it6616_hdmi_regmap_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3135) .reg_bits = 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3136) .val_bits = 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3137) .volatile_table = &it6616_hdmi_volatile_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3138) .cache_type = REGCACHE_NONE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3139) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3140)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3141) static const struct regmap_range it6616_mipi_volatile_ranges[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3142) { .range_min = 0, .range_max = 0xff },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3143) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3145) static const struct regmap_access_table it6616_mipi_volatile_table = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3146) .yes_ranges = it6616_mipi_volatile_ranges,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3147) .n_yes_ranges = ARRAY_SIZE(it6616_mipi_volatile_ranges),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3148) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3149)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3150) static const struct regmap_config it6616_mipi_regmap_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3151) .reg_bits = 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3152) .val_bits = 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3153) .volatile_table = &it6616_mipi_volatile_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3154) .cache_type = REGCACHE_NONE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3155) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3156)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3157) static const struct regmap_range it6616_edid_volatile_ranges[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3158) { .range_min = 0, .range_max = 0xff },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3159) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3160)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3161) static const struct regmap_access_table it6616_edid_volatile_table = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3162) .yes_ranges = it6616_edid_volatile_ranges,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3163) .n_yes_ranges = ARRAY_SIZE(it6616_edid_volatile_ranges),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3164) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3165)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3166) static const struct regmap_config it6616_edid_regmap_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3167) .reg_bits = 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3168) .val_bits = 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3169) .volatile_table = &it6616_edid_volatile_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3170) .cache_type = REGCACHE_NONE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3171) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3172)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3173) static ssize_t attr_buffer_put(char *buf, char *reg_buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3174) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3175) int i = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3176) char *str = buf, *end = buf + PAGE_SIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3177)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3178) str += scnprintf(str, end - str,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3179) " 0x00 0x01 0x02 0x03 0x04 0x05 0x06 0x07");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3180) str += scnprintf(str, end - str,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3181) " 0x08 0x09 0x0A 0x0B 0x0C 0x0D 0x0E 0x0F\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3182) str += scnprintf(str, end - str,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3183) "=============================================");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3184) str += scnprintf(str, end - str,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3185) "=======================================");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3186)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3187) for (i = 0; i < 256; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3188) if (i % 16 == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3189) str += scnprintf(str, end - str, "\n[%02X] ", i & 0xF0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3190) str += scnprintf(str, end - str, "0x%02X ", reg_buf[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3191) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3192) str += scnprintf(str, end - str, "\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3193)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3194) return end - str;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3195) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3196) static ssize_t edid_ram_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3197) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3198) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3199) struct it6616 *it6616 = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3200)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3201) u8 reg_buf[256];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3202)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3203) dev_info(dev, "%s(%x)\n", __func__, it6616->attr_hdmi_reg_bank);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3204)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3205) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3206) it6616_hdmi_edid_ram_get(it6616, reg_buf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3207) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3208)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3209) return attr_buffer_put(buf, reg_buf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3210) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3211)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3212) static ssize_t hdmi_reg_store(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3213) struct device_attribute *attr, const char *buf, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3214) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3215) struct it6616 *it6616 = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3216) int reg_bank;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3217)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3218) if (kstrtoint(buf, 10, ®_bank) < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3219) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3220)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3221) it6616->attr_hdmi_reg_bank = (u8) reg_bank;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3222)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3223) dev_info(dev, "%s() %d, %x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3224) __func__, reg_bank, it6616->attr_hdmi_reg_bank);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3226) return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3227) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3229)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3230) static ssize_t hdmi_reg_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3231) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3232) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3233) struct it6616 *it6616 = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3234) struct regmap *hdmi = it6616->hdmi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3235) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3236) u8 reg_buf[256];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3237)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3238) dev_info(dev, "%s(%x)\n", __func__, it6616->attr_hdmi_reg_bank);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3240) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3241) it6616_hdmi_chgbank(hdmi, it6616->attr_hdmi_reg_bank);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3242) for (i = 0; i < 256; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3243) reg_buf[i] = it6616_hdmi_read(hdmi, i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3244) //regmap_bulk_read(dp, 0, reg_buf, 256);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3245) it6616_hdmi_chgbank(hdmi, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3246) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3247)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3248) return attr_buffer_put(buf, reg_buf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3249) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3250)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3251) static ssize_t mipi_reg_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3252) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3253) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3254) struct it6616 *it6616 = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3255) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3256) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3257) u8 reg_buf[256];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3258)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3259) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3260) for (i = 0; i < 256; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3261) reg_buf[i] = it6616_mipi_tx_read(mipi, i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3262) //regmap_bulk_read(mipi, 0, reg_buf, 256);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3263) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3264)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3265) return attr_buffer_put(buf, reg_buf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3266) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3267)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3268) static ssize_t mipi_reg_store(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3269) struct device_attribute *attr, const char *buf, size_t size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3270) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3271) struct it6616 *it6616 = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3272) struct regmap *mipi = it6616->mipi_regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3273) unsigned int addr, val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3274) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3275)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3276) ret = sscanf(buf, "%X %X ", &addr, &val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3277) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3278) dev_info(dev, "addr= %2.2X\n", addr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3279) dev_info(dev, "val = %2.2X\n", val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3280) if (((addr <= 0xFF) && (addr >= 0x00)) && ((val <= 0xFF) && (val >= 0x00)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3281) regmap_write(mipi, addr, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3282) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3283) dev_info(dev, "it6616_fwrite_mipi_reg , error[%s]\n", buf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3284) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3285)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3286) return size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3287) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3288)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3289) static DEVICE_ATTR_RW(mipi_reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3290) static DEVICE_ATTR_RO(edid_ram);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3291) static DEVICE_ATTR_RW(hdmi_reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3292)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3293) static const struct attribute *it6616_attrs[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3294) &dev_attr_hdmi_reg.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3295) &dev_attr_mipi_reg.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3296) &dev_attr_edid_ram.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3297) NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3298) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3299)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3300) static inline bool tx_5v_power_present(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3301) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3302) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3303)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3304) return it6616_hdmi_is_5v_on(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3305) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3306)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3307) static inline bool no_signal(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3308) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3309) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3310)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3311) v4l2_dbg(1, debug, sd, "%s no signal:%d\n", __func__,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3312) it6616->nosignal);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3313)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3314) return it6616->nosignal;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3315) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3316)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3317) static inline bool audio_present(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3318) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3319) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3320)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3321) return it6616->is_audio_present;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3322) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3323)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3324) static int get_audio_sampling_rate(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3325) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3326) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3327)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3328) if (no_signal(sd))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3329) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3330)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3331) return code_to_rate_table[it6616->ainfo.force_sample_freq];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3332) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3333)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3334) static inline unsigned int fps_calc(const struct v4l2_bt_timings *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3335) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3336) if (!V4L2_DV_BT_FRAME_HEIGHT(t) || !V4L2_DV_BT_FRAME_WIDTH(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3337) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3338)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3339) return DIV_ROUND_CLOSEST((unsigned int)t->pixelclock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3340) V4L2_DV_BT_FRAME_HEIGHT(t) * V4L2_DV_BT_FRAME_WIDTH(t));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3341) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3342)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3343) static bool it6616_rcv_supported_res(struct v4l2_subdev *sd, u32 width,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3344) u32 height)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3345) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3346) u32 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3347)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3348) for (i = 0; i < ARRAY_SIZE(supported_modes); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3349) if ((supported_modes[i].width == width) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3350) (supported_modes[i].height == height)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3351) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3352) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3353) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3354)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3355) if (i == ARRAY_SIZE(supported_modes)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3356) v4l2_err(sd, "%s do not support res wxh: %dx%d\n", __func__,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3357) width, height);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3358) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3359) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3360) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3361) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3362) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3363)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3364) static int it6616_get_detected_timings(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3365) struct v4l2_dv_timings *timings)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3366) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3367) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3368) struct v4l2_bt_timings *bt = &timings->bt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3369) u32 fps, htotal, vtotal;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3370)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3371) memset(timings, 0, sizeof(struct v4l2_dv_timings));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3372) it6616_hdmi_rx_get_video_info(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3373)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3374) it6616->nosignal = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3375) it6616->is_audio_present = tx_5v_power_present(sd) ? true : false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3376) timings->type = V4L2_DV_BT_656_1120;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3377) bt->interlaced = it6616->vinfo.interlaced;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3378) bt->width = it6616->vinfo.h_active;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3379) bt->height = it6616->vinfo.v_active;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3380) bt->vsync = it6616->vinfo.v_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3381) bt->hsync = it6616->vinfo.h_sync_w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3382) bt->pixelclock = it6616->vinfo.pclk * 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3383) bt->hfrontporch = it6616->vinfo.h_front_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3384) bt->vfrontporch = it6616->vinfo.v_front_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3385) bt->hbackporch = it6616->vinfo.h_back_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3386) bt->vbackporch = it6616->vinfo.v_back_porch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3387) htotal = it6616->vinfo.h_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3388) vtotal = it6616->vinfo.v_total;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3389)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3390) if (it6616->avi_if.colorspace == HDMI_COLORSPACE_YUV420) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3391) bt->width = it6616->vinfo.h_active * 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3392) bt->hfrontporch = it6616->vinfo.h_front_porch * 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3393) bt->hbackporch = it6616->vinfo.h_back_porch * 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3394) bt->hsync = it6616->vinfo.h_sync_w * 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3395) htotal = it6616->vinfo.h_total * 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3396) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3397)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3398) fps = fps_calc(bt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3399)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3400) if (!it6616_rcv_supported_res(sd, bt->width, bt->height)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3401) it6616->nosignal = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3402) v4l2_err(sd, "%s: rcv err res, return no signal!\n", __func__);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3403) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3404) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3405)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3406) /* for interlaced res*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3407) if (bt->interlaced) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3408) bt->height *= 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3409) bt->il_vsync = bt->vsync + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3410) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3411)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3412) v4l2_dbg(1, debug, sd, "act:%dx%d, total:%dx%d, pixclk:%d, fps:%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3413) bt->width, bt->height, htotal, vtotal, bt->pixelclock, fps);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3414) v4l2_dbg(1, debug, sd, "hfp:%d, hs:%d, hbp:%d, vfp:%d, vs:%d, vbp:%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3415) bt->hfrontporch, bt->hsync, bt->hbackporch,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3416) bt->vfrontporch, bt->vsync, bt->vbackporch);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3417) v4l2_dbg(1, debug, sd, "inerlaced:%d,\n", bt->interlaced);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3418)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3419) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3420) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3421)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3422) static int it6616_s_ctrl_detect_tx_5v(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3423) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3424) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3425)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3426) return v4l2_ctrl_s_ctrl(it6616->detect_tx_5v_ctrl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3427) tx_5v_power_present(sd));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3428) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3429)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3430) static int it6616_s_ctrl_audio_sampling_rate(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3431) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3432) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3433)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3434) return v4l2_ctrl_s_ctrl(it6616->audio_sampling_rate_ctrl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3435) get_audio_sampling_rate(sd));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3436) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3437)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3438) static int it6616_s_ctrl_audio_present(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3439) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3440) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3441)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3442) return v4l2_ctrl_s_ctrl(it6616->audio_present_ctrl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3443) audio_present(sd));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3444) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3445)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3446) static int it6616_update_controls(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3447) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3448) int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3449)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3450) ret |= it6616_s_ctrl_detect_tx_5v(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3451) ret |= it6616_s_ctrl_audio_sampling_rate(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3452) ret |= it6616_s_ctrl_audio_present(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3453)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3454) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3455) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3456)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3457) static bool it6616_match_dv_timings(const struct v4l2_dv_timings *t1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3458) const struct v4l2_dv_timings *t2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3459) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3460) if (t1->type != t2->type || t1->type != V4L2_DV_BT_656_1120)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3461) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3462) if (t1->bt.width == t2->bt.width &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3463) t1->bt.height == t2->bt.height &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3464) t1->bt.interlaced == t2->bt.interlaced &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3465) t1->bt.hfrontporch == t2->bt.hfrontporch &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3466) t1->bt.hsync == t2->bt.hsync &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3467) t1->bt.hbackporch == t2->bt.hbackporch &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3468) t1->bt.vfrontporch == t2->bt.vfrontporch &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3469) t1->bt.vsync == t2->bt.vsync &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3470) t1->bt.vbackporch == t2->bt.vbackporch &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3471) (!t1->bt.interlaced ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3472) (t1->bt.il_vfrontporch == t2->bt.il_vfrontporch &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3473) t1->bt.il_vsync == t2->bt.il_vsync &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3474) t1->bt.il_vbackporch == t2->bt.il_vbackporch)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3475) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3476) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3477) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3478)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3479) static void it6616_format_change(struct v4l2_subdev *sd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3480) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3481) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3482) struct v4l2_dv_timings timings;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3483) const struct v4l2_event it6616_ev_fmt = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3484) .type = V4L2_EVENT_SOURCE_CHANGE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3485) .u.src_change.changes = V4L2_EVENT_SRC_CH_RESOLUTION,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3486) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3487)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3488) it6616_get_detected_timings(sd, &timings);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3489)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3490) if (!it6616_match_dv_timings(&it6616->timings, &timings)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3491) /* automatically set timing rather than set by user */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3492) it6616_s_dv_timings(sd, &timings);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3493) v4l2_print_dv_timings(sd->name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3494) "Format_change: New format: ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3495) &timings, false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3496) if (sd->devnode)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3497) v4l2_subdev_notify_event(sd, &it6616_ev_fmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3498) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3499) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3500)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3501) static int it6616_isr(struct v4l2_subdev *sd, u32 status, bool *handled)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3502) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3503) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3504) static struct v4l2_dv_timings default_timing =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3505) V4L2_DV_BT_CEA_640X480P59_94;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3506)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3507) if (tx_5v_power_present(sd)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3508) it6616_poll_threaded_handler(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3509) it6616_intp_threaded_handler(0, it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3510) it6616_format_change(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3511) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3512) it6616_s_dv_timings(sd, &default_timing);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3513) it6616->nosignal = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3514) v4l2_dbg(1, debug, sd, "%s: HDMI unplug!!!\n", __func__);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3515) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3516)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3517) *handled = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3518)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3519) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3520) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3521)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3522) static void it6616_work_i2c_poll(struct work_struct *work)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3523) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3524) struct delayed_work *dwork = to_delayed_work(work);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3525) struct it6616 *it6616 = container_of(dwork,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3526) struct it6616, work_i2c_poll);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3527) bool handled;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3528)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3529) it6616_s_ctrl_detect_tx_5v(&it6616->sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3530) it6616_isr(&it6616->sd, 0, &handled);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3531) schedule_delayed_work(&it6616->work_i2c_poll,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3532) msecs_to_jiffies(POLL_INTERVAL_MS));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3533) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3534)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3535) static int it6616_subscribe_event(struct v4l2_subdev *sd, struct v4l2_fh *fh,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3536) struct v4l2_event_subscription *sub)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3537) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3538) switch (sub->type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3539) case V4L2_EVENT_SOURCE_CHANGE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3540) return v4l2_src_change_event_subdev_subscribe(sd, fh, sub);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3541) case V4L2_EVENT_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3542) return v4l2_ctrl_subdev_subscribe_event(sd, fh, sub);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3543) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3544) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3545) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3546) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3547)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3548) static int it6616_g_input_status(struct v4l2_subdev *sd, u32 *status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3549) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3550) *status = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3551) *status |= no_signal(sd) ? V4L2_IN_ST_NO_SIGNAL : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3552)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3553) v4l2_dbg(1, debug, sd, "%s: status = 0x%x\n", __func__, *status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3554)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3555) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3556) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3557)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3558) static int it6616_s_dv_timings(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3559) struct v4l2_dv_timings *timings)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3560) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3561) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3562)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3563) if (!timings)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3564) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3565)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3566) if (debug)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3567) v4l2_print_dv_timings(sd->name, "s_dv_timings: ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3568) timings, false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3569)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3570) if (v4l2_match_dv_timings(&it6616->timings, timings, 0, false)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3571) v4l2_dbg(1, debug, sd, "%s: no change\n", __func__);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3572) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3573) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3574)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3575) if (!v4l2_valid_dv_timings(timings,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3576) &it6616_timings_cap, NULL, NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3577) v4l2_dbg(1, debug, sd, "%s: timings out of range\n", __func__);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3578) return -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3579) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3581) it6616->timings = *timings;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3582)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3583) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3584) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3585)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3586) static int it6616_g_dv_timings(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3587) struct v4l2_dv_timings *timings)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3588) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3589) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3590)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3591) *timings = it6616->timings;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3592)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3593) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3594) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3595)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3596) static int it6616_enum_dv_timings(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3597) struct v4l2_enum_dv_timings *timings)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3598) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3599) if (timings->pad != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3600) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3601)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3602) return v4l2_enum_dv_timings_cap(timings,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3603) &it6616_timings_cap, NULL, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3604) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3605)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3606) static int it6616_query_dv_timings(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3607) struct v4l2_dv_timings *timings)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3608) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3609) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3610)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3611) *timings = it6616->timings;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3612) if (debug)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3613) v4l2_print_dv_timings(sd->name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3614) "query_dv_timings: ", timings, false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3615)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3616) if (!v4l2_valid_dv_timings(timings, &it6616_timings_cap, NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3617) NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3618) v4l2_dbg(1, debug, sd, "%s: timings out of range\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3619) __func__);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3620)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3621) return -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3622) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3623)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3624) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3625) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3626)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3627) static int it6616_dv_timings_cap(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3628) struct v4l2_dv_timings_cap *cap)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3629) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3630) if (cap->pad != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3631) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3632)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3633) *cap = it6616_timings_cap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3634)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3635) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3636) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3637)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3638) static int it6616_g_mbus_config(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3639) unsigned int pad, struct v4l2_mbus_config *cfg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3640) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3641) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3642)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3643) cfg->type = V4L2_MBUS_CSI2_DPHY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3644) cfg->flags = V4L2_MBUS_CSI2_NONCONTINUOUS_CLOCK |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3645) V4L2_MBUS_CSI2_CHANNEL_0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3646)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3647) switch (it6616->csi_lanes_in_use) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3648) case 1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3649) cfg->flags |= V4L2_MBUS_CSI2_1_LANE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3650) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3651) case 2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3652) cfg->flags |= V4L2_MBUS_CSI2_2_LANE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3653) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3654) case 3:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3655) cfg->flags |= V4L2_MBUS_CSI2_3_LANE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3656) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3657) case 4:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3658) cfg->flags |= V4L2_MBUS_CSI2_4_LANE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3659) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3660)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3661) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3662) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3663) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3664)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3665) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3666) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3667)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3668) static int __it6616_start_stream(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3669) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3670) it6616_mipitx_output_disable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3671) usleep_range(1000, 2000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3672) it6616_mipi_tx_output_enable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3673)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3674) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3675) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3676)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3677) static int __it6616_stop_stream(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3678) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3679) it6616_mipitx_output_disable(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3680)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3681) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3682) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3683)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3684) static int it6616_s_stream(struct v4l2_subdev *sd, int on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3685) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3686) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3687) struct i2c_client *client = it6616->i2c_client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3688) int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3689)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3690) dev_info(&client->dev, "%s: on: %d, %dx%d@%d\n", __func__, on,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3691) it6616->cur_mode->width,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3692) it6616->cur_mode->height,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3693) DIV_ROUND_CLOSEST(it6616->cur_mode->max_fps.denominator,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3694) it6616->cur_mode->max_fps.numerator));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3695)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3696) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3697) on = !!on;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3698)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3699) if (on) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3700) ret = __it6616_start_stream(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3701) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3702) dev_err(it6616->dev, "Failed to start it6616 stream\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3703) goto unlock_and_return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3704) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3705) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3706) __it6616_stop_stream(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3707) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3708)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3709)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3710) unlock_and_return:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3711) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3712) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3713) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3714)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3715) static int it6616_enum_mbus_code(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3716) struct v4l2_subdev_pad_config *cfg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3717) struct v4l2_subdev_mbus_code_enum *code)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3718) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3719) switch (code->index) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3720) case 0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3721) code->code = IT6616_MEDIA_BUS_FMT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3722) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3723)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3724) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3725) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3726) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3727)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3728) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3729) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3730)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3731) static int it6616_enum_frame_sizes(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3732) struct v4l2_subdev_pad_config *cfg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3733) struct v4l2_subdev_frame_size_enum *fse)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3734) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3735) if (fse->index >= ARRAY_SIZE(supported_modes))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3736) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3737)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3738) if (fse->code != IT6616_MEDIA_BUS_FMT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3739) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3740)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3741) fse->min_width = supported_modes[fse->index].width;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3742) fse->max_width = supported_modes[fse->index].width;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3743) fse->max_height = supported_modes[fse->index].height;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3744) fse->min_height = supported_modes[fse->index].height;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3745)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3746) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3747) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3748)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3749) static int it6616_get_fmt(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3750) struct v4l2_subdev_pad_config *cfg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3751) struct v4l2_subdev_format *format)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3752) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3753) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3754)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3755) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3756) format->format.code = it6616->mbus_fmt_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3757) format->format.width = it6616->timings.bt.width;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3758) format->format.height = it6616->timings.bt.height;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3759) format->format.field =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3760) it6616->timings.bt.interlaced ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3761) V4L2_FIELD_INTERLACED : V4L2_FIELD_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3762) format->format.colorspace = V4L2_COLORSPACE_SRGB;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3763) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3764)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3765) v4l2_dbg(1, debug, sd, "%s: fmt code:%d, w:%d, h:%d, field code:%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3766) __func__, format->format.code, format->format.width,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3767) format->format.height, format->format.field);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3768)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3769) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3770) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3771)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3772) static int it6616_enum_frame_interval(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3773) struct v4l2_subdev_pad_config *cfg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3774) struct v4l2_subdev_frame_interval_enum *fie)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3775) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3776) if (fie->index >= ARRAY_SIZE(supported_modes))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3777) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3778)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3779) if (fie->code != IT6616_MEDIA_BUS_FMT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3780) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3781)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3782) fie->width = supported_modes[fie->index].width;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3783) fie->height = supported_modes[fie->index].height;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3784) fie->interval = supported_modes[fie->index].max_fps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3785)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3786) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3787) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3788)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3789) static int it6616_get_reso_dist(const struct it6616_mode *mode,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3790) struct v4l2_mbus_framefmt *framefmt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3791) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3792) return abs(mode->width - framefmt->width) +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3793) abs(mode->height - framefmt->height);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3794) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3795)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3796) static const struct it6616_mode *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3797) it6616_find_best_fit(struct v4l2_subdev_format *fmt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3798) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3799) struct v4l2_mbus_framefmt *framefmt = &fmt->format;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3800) int dist;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3801) int cur_best_fit = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3802) int cur_best_fit_dist = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3803) unsigned int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3804)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3805) for (i = 0; i < ARRAY_SIZE(supported_modes); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3806) dist = it6616_get_reso_dist(&supported_modes[i], framefmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3807) if (cur_best_fit_dist == -1 || dist < cur_best_fit_dist) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3808) cur_best_fit_dist = dist;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3809) cur_best_fit = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3810) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3811) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3812)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3813) return &supported_modes[cur_best_fit];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3814) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3815)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3816) static int it6616_set_fmt(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3817) struct v4l2_subdev_pad_config *cfg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3818) struct v4l2_subdev_format *format)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3819) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3820) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3821) const struct it6616_mode *mode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3822)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3823) /* is overwritten by get_fmt */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3824) u32 code = format->format.code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3825) int ret = it6616_get_fmt(sd, cfg, format);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3826)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3827) format->format.code = code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3828)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3829) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3830) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3831)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3832) switch (code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3833) case IT6616_MEDIA_BUS_FMT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3834) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3835)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3836) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3837) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3838) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3839)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3840) if (format->which == V4L2_SUBDEV_FORMAT_TRY)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3841) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3842)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3843) it6616->mbus_fmt_code = format->format.code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3844) mode = it6616_find_best_fit(format);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3845) it6616->cur_mode = mode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3846)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3847) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3848) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3849)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3850) static int it6616_g_frame_interval(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3851) struct v4l2_subdev_frame_interval *fi)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3852) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3853) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3854) const struct it6616_mode *mode = it6616->cur_mode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3855)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3856) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3857) fi->interval = mode->max_fps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3858) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3859)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3860) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3861) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3862)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3863) static void it6616_get_module_inf(struct it6616 *it6616,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3864) struct rkmodule_inf *inf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3865) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3866) memset(inf, 0, sizeof(*inf));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3867) strscpy(inf->base.sensor, IT6616_NAME, sizeof(inf->base.sensor));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3868) strscpy(inf->base.module, it6616->module_name, sizeof(inf->base.module));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3869) strscpy(inf->base.lens, it6616->len_name, sizeof(inf->base.lens));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3870) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3871)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3872) static long it6616_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3873) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3874) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3875) long ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3876)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3877) switch (cmd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3878) case RKMODULE_GET_MODULE_INFO:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3879) it6616_get_module_inf(it6616, (struct rkmodule_inf *)arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3880) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3881) case RKMODULE_GET_HDMI_MODE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3882) *(int *)arg = RKMODULE_HDMIIN_MODE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3883) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3884) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3885) ret = -ENOIOCTLCMD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3886) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3887) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3888)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3889) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3890) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3891)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3892) static int it6616_s_power(struct v4l2_subdev *sd, int on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3893) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3894) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3895) int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3896)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3897) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3898)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3899) if (it6616->power_on == !!on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3900) goto unlock_and_return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3901)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3902) if (on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3903) it6616->power_on = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3904) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3905) it6616->power_on = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3906)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3907) unlock_and_return:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3908) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3909)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3910) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3911) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3912)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3913) #ifdef CONFIG_COMPAT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3914) static long it6616_compat_ioctl32(struct v4l2_subdev *sd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3915) unsigned int cmd, unsigned long arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3916) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3917) void __user *up = compat_ptr(arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3918) struct rkmodule_inf *inf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3919) long ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3920) int *seq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3921)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3922) switch (cmd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3923) case RKMODULE_GET_MODULE_INFO:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3924) inf = kzalloc(sizeof(*inf), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3925) if (!inf) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3926) ret = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3927) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3928) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3929)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3930) ret = it6616_ioctl(sd, cmd, inf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3931) if (!ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3932) ret = copy_to_user(up, inf, sizeof(*inf));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3933) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3934) ret = -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3935) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3936) kfree(inf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3937) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3938) case RKMODULE_GET_HDMI_MODE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3939) seq = kzalloc(sizeof(*seq), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3940) if (!seq) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3941) ret = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3942) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3943) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3944)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3945) ret = it6616_ioctl(sd, cmd, seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3946) if (!ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3947) ret = copy_to_user(up, seq, sizeof(*seq));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3948) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3949) ret = -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3950) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3951) kfree(seq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3952) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3953) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3954) ret = -ENOIOCTLCMD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3955) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3956) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3957)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3958) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3959) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3960) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3961)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3962) #ifdef CONFIG_VIDEO_V4L2_SUBDEV_API
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3963) static int it6616_open(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3964) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3965) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3966) struct v4l2_mbus_framefmt *try_fmt =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3967) v4l2_subdev_get_try_format(sd, fh->pad, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3968) const struct it6616_mode *def_mode = &supported_modes[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3969)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3970) mutex_lock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3971) /* Initialize try_fmt */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3972) try_fmt->width = def_mode->width;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3973) try_fmt->height = def_mode->height;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3974) try_fmt->code = IT6616_MEDIA_BUS_FMT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3975) try_fmt->field = V4L2_FIELD_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3976) mutex_unlock(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3977)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3978) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3979) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3980) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3981)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3982) #ifdef CONFIG_VIDEO_V4L2_SUBDEV_API
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3983) static const struct v4l2_subdev_internal_ops it6616_internal_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3984) .open = it6616_open,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3985) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3986) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3987)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3988) static const struct v4l2_subdev_core_ops it6616_core_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3989) .s_power = it6616_s_power,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3990) .interrupt_service_routine = it6616_isr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3991) .subscribe_event = it6616_subscribe_event,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3992) .unsubscribe_event = v4l2_event_subdev_unsubscribe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3993) .ioctl = it6616_ioctl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3994) #ifdef CONFIG_COMPAT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3995) .compat_ioctl32 = it6616_compat_ioctl32,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3996) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3997) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3998)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3999) static const struct v4l2_subdev_video_ops it6616_video_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4000) .g_input_status = it6616_g_input_status,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4001) .s_dv_timings = it6616_s_dv_timings,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4002) .g_dv_timings = it6616_g_dv_timings,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4003) .query_dv_timings = it6616_query_dv_timings,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4004) .s_stream = it6616_s_stream,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4005) .g_frame_interval = it6616_g_frame_interval,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4006) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4007)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4008) static const struct v4l2_subdev_pad_ops it6616_pad_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4009) .enum_mbus_code = it6616_enum_mbus_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4010) .enum_frame_size = it6616_enum_frame_sizes,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4011) .enum_frame_interval = it6616_enum_frame_interval,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4012) .set_fmt = it6616_set_fmt,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4013) .get_fmt = it6616_get_fmt,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4014) .enum_dv_timings = it6616_enum_dv_timings,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4015) .dv_timings_cap = it6616_dv_timings_cap,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4016) .get_mbus_config = it6616_g_mbus_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4017) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4018)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4019) static const struct v4l2_subdev_ops it6616_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4020) .core = &it6616_core_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4021) .video = &it6616_video_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4022) .pad = &it6616_pad_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4023) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4024)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4025) static const struct v4l2_ctrl_config it6616_ctrl_audio_sampling_rate = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4026) .id = RK_V4L2_CID_AUDIO_SAMPLING_RATE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4027) .name = "Audio sampling rate",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4028) .type = V4L2_CTRL_TYPE_INTEGER,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4029) .min = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4030) .max = 768000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4031) .step = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4032) .def = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4033) .flags = V4L2_CTRL_FLAG_READ_ONLY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4034) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4035)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4036) static const struct v4l2_ctrl_config it6616_ctrl_audio_present = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4037) .id = RK_V4L2_CID_AUDIO_PRESENT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4038) .name = "Audio present",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4039) .type = V4L2_CTRL_TYPE_BOOLEAN,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4040) .min = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4041) .max = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4042) .step = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4043) .def = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4044) .flags = V4L2_CTRL_FLAG_READ_ONLY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4045) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4046)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4047) static void it6616_reset(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4048) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4049) gpiod_set_value(it6616->reset_gpio, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4050) usleep_range(2000, 2100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4051) gpiod_set_value(it6616->reset_gpio, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4052) usleep_range(120*1000, 121*1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4053) gpiod_set_value(it6616->reset_gpio, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4054) usleep_range(300*1000, 310*1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4055) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4056)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4057) static int it6616_init_v4l2_ctrls(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4058) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4059) struct v4l2_subdev *sd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4060) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4061)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4062) sd = &it6616->sd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4063) ret = v4l2_ctrl_handler_init(&it6616->hdl, 5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4064) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4065) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4066)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4067) it6616->link_freq = v4l2_ctrl_new_int_menu(&it6616->hdl, NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4068) V4L2_CID_LINK_FREQ,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4069) ARRAY_SIZE(link_freq_menu_items) - 1, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4070) link_freq_menu_items);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4071) it6616->pixel_rate = v4l2_ctrl_new_std(&it6616->hdl, NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4072) V4L2_CID_PIXEL_RATE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4073) 0, IT6616_PIXEL_RATE, 1, IT6616_PIXEL_RATE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4074)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4075) it6616->detect_tx_5v_ctrl = v4l2_ctrl_new_std(&it6616->hdl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4076) NULL, V4L2_CID_DV_RX_POWER_PRESENT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4077) 0, 1, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4078)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4079) it6616->audio_sampling_rate_ctrl =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4080) v4l2_ctrl_new_custom(&it6616->hdl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4081) &it6616_ctrl_audio_sampling_rate, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4082) it6616->audio_present_ctrl = v4l2_ctrl_new_custom(&it6616->hdl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4083) &it6616_ctrl_audio_present, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4084)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4085) sd->ctrl_handler = &it6616->hdl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4086) if (it6616->hdl.error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4087) ret = it6616->hdl.error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4088) v4l2_err(sd, "cfg v4l2 ctrls failed! ret:%d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4089) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4090) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4091)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4092) __v4l2_ctrl_s_ctrl(it6616->link_freq, link_freq_menu_items[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4093) __v4l2_ctrl_s_ctrl_int64(it6616->pixel_rate, IT6616_PIXEL_RATE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4094)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4095) if (it6616_update_controls(sd)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4096) ret = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4097) v4l2_err(sd, "update v4l2 ctrls failed! ret:%d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4098) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4099) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4100)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4101) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4102) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4103)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4104) #ifdef CONFIG_OF
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4105) static int it6616_probe_of(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4106) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4107) struct device *dev = &it6616->i2c_client->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4108) struct device_node *node = dev->of_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4109) struct v4l2_fwnode_endpoint endpoint = { .bus_type = 0 };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4110) struct device_node *ep;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4111) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4112)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4113) ret = of_property_read_u32(node, RKMODULE_CAMERA_MODULE_INDEX,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4114) &it6616->module_index);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4115) ret |= of_property_read_string(node, RKMODULE_CAMERA_MODULE_FACING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4116) &it6616->module_facing);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4117) ret |= of_property_read_string(node, RKMODULE_CAMERA_MODULE_NAME,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4118) &it6616->module_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4119) ret |= of_property_read_string(node, RKMODULE_CAMERA_LENS_NAME,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4120) &it6616->len_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4121) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4122) dev_err(dev, "could not get module information!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4123) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4124) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4125)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4126) it6616->power_gpio = devm_gpiod_get_optional(dev, "power",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4127) GPIOD_OUT_LOW);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4128) if (IS_ERR(it6616->power_gpio)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4129) dev_err(dev, "failed to get power gpio\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4130) ret = PTR_ERR(it6616->power_gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4131) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4132) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4133)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4134) it6616->reset_gpio = devm_gpiod_get_optional(dev, "reset",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4135) GPIOD_OUT_HIGH);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4136) if (IS_ERR(it6616->reset_gpio)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4137) dev_err(dev, "failed to get reset gpio\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4138) ret = PTR_ERR(it6616->reset_gpio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4139) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4140) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4141)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4142) ep = of_graph_get_next_endpoint(dev->of_node, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4143) if (!ep) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4144) dev_err(dev, "missing endpoint node\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4145) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4146) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4147)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4148) ret = v4l2_fwnode_endpoint_alloc_parse(of_fwnode_handle(ep), &endpoint);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4149) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4150) dev_err(dev, "failed to parse endpoint\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4151) goto put_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4152) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4154) if (endpoint.bus_type != V4L2_MBUS_CSI2_DPHY ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4155) endpoint.bus.mipi_csi2.num_data_lanes == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4156) dev_err(dev, "missing CSI-2 properties in endpoint\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4157) ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4158) goto free_endpoint;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4159) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4160)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4161) it6616->xvclk = devm_clk_get(dev, "xvclk");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4162) if (IS_ERR(it6616->xvclk)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4163) dev_err(dev, "failed to get xvclk\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4164) ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4165) goto free_endpoint;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4166) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4167)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4168) ret = clk_prepare_enable(it6616->xvclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4169) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4170) dev_err(dev, "Failed! to enable xvclk\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4171) goto free_endpoint;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4172) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4173)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4174) it6616->csi_lanes_in_use = endpoint.bus.mipi_csi2.num_data_lanes;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4175) it6616->bus = endpoint.bus.mipi_csi2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4176)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4177) gpiod_set_value(it6616->power_gpio, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4178) it6616_reset(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4179)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4180) ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4181)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4182) free_endpoint:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4183) v4l2_fwnode_endpoint_free(&endpoint);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4184) put_node:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4185) of_node_put(ep);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4186) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4187) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4188) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4189) static inline int it6616_probe_of(struct it6616 *state)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4190) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4191) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4192) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4193) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4194)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4195) static ssize_t audio_present_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4196) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4197) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4198) struct it6616 *it6616 = g_it6616;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4199)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4200) return snprintf(buf, PAGE_SIZE, "%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4201) tx_5v_power_present(&it6616->sd) ? 1 : 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4202) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4204) static ssize_t audio_rate_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4205) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4206) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4207) struct it6616 *it6616 = g_it6616;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4208)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4209) return snprintf(buf, PAGE_SIZE, "%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4210) code_to_rate_table[it6616->ainfo.force_sample_freq]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4211) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4212)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4213) static DEVICE_ATTR_RO(audio_present);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4214) static DEVICE_ATTR_RO(audio_rate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4215)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4216) static int it6616_create_class_attr(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4217) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4218) int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4220) it6616->hdmirx_class = class_create(THIS_MODULE, "hdmirx_it6616");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4221) if (IS_ERR(it6616->hdmirx_class)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4222) ret = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4223) dev_err(it6616->dev, "failed to create hdmirx_it6616 class!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4224) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4225) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4226)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4227) it6616->classdev = device_create(it6616->hdmirx_class, NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4228) MKDEV(0, 0), NULL, "hdmirx_it6616");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4229) if (IS_ERR(it6616->classdev)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4230) ret = PTR_ERR(it6616->classdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4231) dev_err(it6616->dev, "Failed to create device\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4232) goto err1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4233) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4234)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4235) ret = device_create_file(it6616->classdev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4236) &dev_attr_audio_present);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4237) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4238) dev_err(it6616->dev, "failed to create attr audio_present!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4239) goto err1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4240) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4241)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4242) ret = device_create_file(it6616->classdev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4243) &dev_attr_audio_rate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4244) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4245) dev_err(it6616->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4246) "failed to create attr audio_rate!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4247) goto err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4248) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4249)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4250) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4251)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4252) err:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4253) device_remove_file(it6616->classdev, &dev_attr_audio_present);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4254) err1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4255) class_destroy(it6616->hdmirx_class);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4256) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4257) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4258)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4259) static void it6616_remove_class_attr(struct it6616 *it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4260) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4261) device_remove_file(it6616->classdev, &dev_attr_audio_rate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4262) device_remove_file(it6616->classdev, &dev_attr_audio_present);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4263) class_destroy(it6616->hdmirx_class);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4264) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4265)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4266) static int it6616_probe(struct i2c_client *client,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4267) const struct i2c_device_id *id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4268) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4269) struct it6616 *it6616;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4270) struct v4l2_subdev *sd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4271) struct device *dev = &client->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4272) char facing[2];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4273) int err = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4274)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4275) dev_info(dev, "driver version: %02x.%02x.%02x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4276) DRIVER_VERSION >> 16,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4277) (DRIVER_VERSION & 0xff00) >> 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4278) DRIVER_VERSION & 0x00ff);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4279)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4280) it6616 = devm_kzalloc(dev, sizeof(struct it6616), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4281) if (!it6616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4282) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4283)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4284) sd = &it6616->sd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4285) it6616->hdmi_i2c = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4286) it6616->mipi_i2c = i2c_new_dummy_device(client->adapter,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4287) I2C_ADR_MIPI >> 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4288)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4289) if (!it6616->mipi_i2c)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4290) return -EIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4291)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4292) it6616->edid_i2c = i2c_new_dummy_device(client->adapter,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4293) I2C_ADR_EDID >> 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4294)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4295) if (!it6616->edid_i2c)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4296) goto unregister_mipi_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4297)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4298) it6616->hdmi_regmap = devm_regmap_init_i2c(client,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4299) &it6616_hdmi_regmap_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4300) if (IS_ERR(it6616->hdmi_i2c)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4301) err = PTR_ERR(it6616->hdmi_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4302) goto unregister_edid_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4303) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4304)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4305) it6616->mipi_regmap = devm_regmap_init_i2c(it6616->mipi_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4306) &it6616_mipi_regmap_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4307) if (IS_ERR(it6616->mipi_regmap)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4308) err = PTR_ERR(it6616->mipi_regmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4309) goto unregister_edid_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4310) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4311)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4312) it6616->edid_regmap = devm_regmap_init_i2c(it6616->edid_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4313) &it6616_edid_regmap_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4314) if (IS_ERR(it6616->edid_regmap)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4315) err = PTR_ERR(it6616->edid_regmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4316) goto unregister_edid_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4317) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4318)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4319) it6616->dev = dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4320) it6616->cur_mode = &supported_modes[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4321) it6616->i2c_client = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4322) it6616->mbus_fmt_code = IT6616_MEDIA_BUS_FMT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4323) err = it6616_probe_of(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4324) if (err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4325) v4l2_err(sd, "it6616_parse_of failed! err:%d\n", err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4326) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4327) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4328) it6616_reset(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4329)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4330) mutex_init(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4331)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4332) err = it6616_initial(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4333) if (err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4334) dev_err(dev, "it6616_initial failed: %d", err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4335) err = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4336) goto unregister_edid_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4337) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4338)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4339) err = sysfs_create_files(&client->dev.kobj, it6616_attrs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4340) if (err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4341) dev_err(dev, "sysfs_create_files failed: %d", err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4342) goto unregister_edid_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4343) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4344)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4345) i2c_set_clientdata(client, it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4346) usleep_range(3000, 6000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4347)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4348) err = it6616_init_v4l2_ctrls(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4349) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4350) goto err_free_hdl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4351)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4352) client->flags |= I2C_CLIENT_SCCB;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4353) #ifdef CONFIG_VIDEO_V4L2_SUBDEV_API
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4354) v4l2_i2c_subdev_init(sd, client, &it6616_ops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4355) sd->internal_ops = &it6616_internal_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4356) sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE | V4L2_SUBDEV_FL_HAS_EVENTS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4357) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4358)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4359) #if defined(CONFIG_MEDIA_CONTROLLER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4360) it6616->pad.flags = MEDIA_PAD_FL_SOURCE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4361) sd->entity.function = MEDIA_ENT_F_CAM_SENSOR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4362) err = media_entity_pads_init(&sd->entity, 1, &it6616->pad);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4363) if (err < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4364) v4l2_err(sd, "media entity init failed! err:%d\n", err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4365) goto err_free_hdl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4366) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4367) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4368) memset(facing, 0, sizeof(facing));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4369) if (strcmp(it6616->module_facing, "back") == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4370) facing[0] = 'b';
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4371) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4372) facing[0] = 'f';
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4373)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4374) snprintf(sd->name, sizeof(sd->name), "m%02d_%s_%s %s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4375) it6616->module_index, facing,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4376) IT6616_NAME, dev_name(sd->dev));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4377) err = v4l2_async_register_subdev_sensor_common(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4378) if (err < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4379) v4l2_err(sd, "v4l2 register subdev failed! err:%d\n", err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4380) goto err_clean_entity;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4381) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4382)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4383) err = it6616_create_class_attr(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4384) if (err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4385) dev_err(it6616->dev, "create class attr failed! err:%d\n", err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4386) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4387) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4388)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4389) INIT_DELAYED_WORK(&it6616->work_i2c_poll, it6616_work_i2c_poll);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4390) schedule_delayed_work(&it6616->work_i2c_poll, msecs_to_jiffies(500));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4391) err = v4l2_ctrl_handler_setup(sd->ctrl_handler);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4392) if (err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4393) v4l2_err(sd, "v4l2 ctrl handler setup failed! err:%d\n", err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4394) goto err_work_queues;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4395) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4396)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4397) v4l2_info(sd, "%s found @ 0x%x (%s)\n", client->name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4398) client->addr << 1, client->adapter->name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4399) g_it6616 = it6616;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4400)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4401) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4402)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4403) err_work_queues:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4404) cancel_delayed_work_sync(&it6616->work_i2c_poll);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4405) err_clean_entity:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4406) #if defined(CONFIG_MEDIA_CONTROLLER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4407) media_entity_cleanup(&sd->entity);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4408) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4409) err_free_hdl:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4410) v4l2_ctrl_handler_free(&it6616->hdl);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4411) mutex_destroy(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4412) unregister_edid_i2c:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4413) i2c_unregister_device(it6616->edid_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4414) unregister_mipi_i2c:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4415) i2c_unregister_device(it6616->mipi_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4416)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4417) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4418) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4419)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4420) static int it6616_remove(struct i2c_client *client)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4421) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4422) struct v4l2_subdev *sd = i2c_get_clientdata(client);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4423) struct it6616 *it6616 = to_it6616(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4424)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4425) cancel_delayed_work_sync(&it6616->work_i2c_poll);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4426) it6616_remove_class_attr(it6616);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4427) v4l2_async_unregister_subdev(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4428) v4l2_device_unregister_subdev(sd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4429) #if defined(CONFIG_MEDIA_CONTROLLER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4430) media_entity_cleanup(&sd->entity);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4431) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4432) v4l2_ctrl_handler_free(&it6616->hdl);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4433) sysfs_remove_files(&client->dev.kobj, it6616_attrs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4434) mutex_destroy(&it6616->confctl_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4435)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4436) i2c_unregister_device(it6616->mipi_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4437) i2c_unregister_device(it6616->edid_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4438) clk_disable_unprepare(it6616->xvclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4439)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4440) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4441) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4442)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4443) #if IS_ENABLED(CONFIG_OF)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4444) static const struct of_device_id it6616_of_match[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4445) { .compatible = "ite,it6616" },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4446) {},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4447) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4448) MODULE_DEVICE_TABLE(of, it6616_of_match);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4449) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4450)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4451) static struct i2c_driver it6616_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4452) .driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4453) .name = IT6616_NAME,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4454) .of_match_table = of_match_ptr(it6616_of_match),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4455) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4456) .probe = it6616_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4457) .remove = it6616_remove,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4458) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4459)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4460) static int __init it6616_driver_init(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4461) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4462) return i2c_add_driver(&it6616_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4463) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4464)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4465) static void __exit it6616_driver_exit(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4466) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4467) i2c_del_driver(&it6616_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4468) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4469)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4470) device_initcall_sync(it6616_driver_init);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4471) module_exit(it6616_driver_exit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4472)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4473) MODULE_DESCRIPTION("ITE it6616 HDMI to CSI-2 bridge driver");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4474) MODULE_AUTHOR("Jianwei Fan <jianwei.fan@rock-chips.com>");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4475) MODULE_AUTHOR("Kenneth Hung<Kenneth.Hung@ite.com.tw>");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4476) MODULE_LICENSE("GPL");