Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^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) 2017-2020 Jacopo Mondi
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  * Copyright (C) 2017-2020 Kieran Bingham
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  * Copyright (C) 2017-2020 Laurent Pinchart
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  * Copyright (C) 2017-2020 Niklas Söderlund
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7)  * Copyright (C) 2016 Renesas Electronics Corporation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8)  * Copyright (C) 2015 Cogent Embedded, Inc.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10)  * This file exports functions to control the Maxim MAX9271 GMSL serializer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11)  * chip. This is not a self-contained driver, as MAX9271 is usually embedded in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12)  * camera modules with at least one image sensor and optional additional
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13)  * components, such as uController units or ISPs/DSPs.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15)  * Drivers for the camera modules (i.e. rdacm20/21) are expected to use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16)  * functions exported from this library driver to maximize code re-use.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) #include <linux/delay.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) #include <linux/i2c.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) #include "max9271.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) static int max9271_read(struct max9271_device *dev, u8 reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) 	dev_dbg(&dev->client->dev, "%s(0x%02x)\n", __func__, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) 	ret = i2c_smbus_read_byte_data(dev->client, reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) 	if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) 		dev_dbg(&dev->client->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) 			"%s: register 0x%02x read failed (%d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) 			__func__, reg, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) static int max9271_write(struct max9271_device *dev, u8 reg, u8 val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) 	dev_dbg(&dev->client->dev, "%s(0x%02x, 0x%02x)\n", __func__, reg, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) 	ret = i2c_smbus_write_byte_data(dev->client, reg, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) 	if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 		dev_err(&dev->client->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) 			"%s: register 0x%02x write failed (%d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) 			__func__, reg, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55)  * max9271_pclk_detect() - Detect valid pixel clock from image sensor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57)  * Wait up to 10ms for a valid pixel clock.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59)  * Returns 0 for success, < 0 for pixel clock not properly detected
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) static int max9271_pclk_detect(struct max9271_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) 	unsigned int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) 	for (i = 0; i < 100; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 		ret = max9271_read(dev, 0x15);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) 		if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 			return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 		if (ret & MAX9271_PCLKDET)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 			return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 		usleep_range(50, 100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 	dev_err(&dev->client->dev, "Unable to detect valid pixel clock\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 	return -EIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) int max9271_set_serial_link(struct max9271_device *dev, bool enable)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 	u8 val = MAX9271_REVCCEN | MAX9271_FWDCCEN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 	if (enable) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 		ret = max9271_pclk_detect(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 			return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 		val |= MAX9271_SEREN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 		val |= MAX9271_CLINKEN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 	 * The serializer temporarily disables the reverse control channel for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 	 * 350µs after starting/stopping the forward serial link, but the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 	 * deserializer synchronization time isn't clearly documented.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) 	 *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 	 * According to the serializer datasheet we should wait 3ms, while
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 	 * according to the deserializer datasheet we should wait 5ms.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) 	 *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) 	 * Short delays here appear to show bit-errors in the writes following.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) 	 * Therefore a conservative delay seems best here.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) 	max9271_write(dev, 0x04, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) 	usleep_range(5000, 8000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) EXPORT_SYMBOL_GPL(max9271_set_serial_link);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) int max9271_configure_i2c(struct max9271_device *dev, u8 i2c_config)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 	ret = max9271_write(dev, 0x0d, i2c_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) 	/* The delay required after an I2C bus configuration change is not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 	 * characterized in the serializer manual. Sleep up to 5msec to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 	 * stay safe.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) EXPORT_SYMBOL_GPL(max9271_configure_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) int max9271_set_high_threshold(struct max9271_device *dev, bool enable)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 	ret = max9271_read(dev, 0x08);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 	if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 	 * Enable or disable reverse channel high threshold to increase
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 	 * immunity to power supply noise.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) 	max9271_write(dev, 0x08, enable ? ret | BIT(0) : ret & ~BIT(0));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 	usleep_range(2000, 2500);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) EXPORT_SYMBOL_GPL(max9271_set_high_threshold);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) int max9271_configure_gmsl_link(struct max9271_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) 	 * Configure the GMSL link:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) 	 *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) 	 * - Double input mode, high data rate, 24-bit mode
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) 	 * - Latch input data on PCLKIN rising edge
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) 	 * - Enable HS/VS encoding
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 	 * - 1-bit parity error detection
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) 	 *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) 	 * TODO: Make the GMSL link configuration parametric.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) 	max9271_write(dev, 0x07, MAX9271_DBL | MAX9271_HVEN |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 		      MAX9271_EDC_1BIT_PARITY);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) 	usleep_range(5000, 8000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) 	 * Adjust spread spectrum to +4% and auto-detect pixel clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) 	 * and serial link rate.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 	max9271_write(dev, 0x02, MAX9271_SPREAD_SPECT_4 | MAX9271_R02_RES |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 		      MAX9271_PCLK_AUTODETECT | MAX9271_SERIAL_AUTODETECT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 	usleep_range(5000, 8000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) EXPORT_SYMBOL_GPL(max9271_configure_gmsl_link);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) int max9271_set_gpios(struct max9271_device *dev, u8 gpio_mask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 	ret = max9271_read(dev, 0x0f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) 	if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 	ret |= gpio_mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 	ret = max9271_write(dev, 0x0f, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 		dev_err(&dev->client->dev, "Failed to set gpio (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) EXPORT_SYMBOL_GPL(max9271_set_gpios);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) int max9271_clear_gpios(struct max9271_device *dev, u8 gpio_mask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 	ret = max9271_read(dev, 0x0f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 	if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 	ret &= ~gpio_mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 	ret = max9271_write(dev, 0x0f, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) 		dev_err(&dev->client->dev, "Failed to clear gpio (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) EXPORT_SYMBOL_GPL(max9271_clear_gpios);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) int max9271_enable_gpios(struct max9271_device *dev, u8 gpio_mask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 	ret = max9271_read(dev, 0x0e);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 	if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 	/* BIT(0) reserved: GPO is always enabled. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 	ret |= (gpio_mask & ~BIT(0));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 	ret = max9271_write(dev, 0x0e, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 		dev_err(&dev->client->dev, "Failed to enable gpio (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) EXPORT_SYMBOL_GPL(max9271_enable_gpios);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) int max9271_disable_gpios(struct max9271_device *dev, u8 gpio_mask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 	ret = max9271_read(dev, 0x0e);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 	if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) 	/* BIT(0) reserved: GPO cannot be disabled */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 	ret &= ~(gpio_mask | BIT(0));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) 	ret = max9271_write(dev, 0x0e, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 		dev_err(&dev->client->dev, "Failed to disable gpio (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) EXPORT_SYMBOL_GPL(max9271_disable_gpios);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) int max9271_verify_id(struct max9271_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) 	ret = max9271_read(dev, 0x1e);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) 		dev_err(&dev->client->dev, "MAX9271 ID read failed (%d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) 			ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) 	if (ret != MAX9271_ID) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) 		dev_err(&dev->client->dev, "MAX9271 ID mismatch (0x%02x)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) 			ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) 		return -ENXIO;
^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) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) EXPORT_SYMBOL_GPL(max9271_verify_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) int max9271_set_address(struct max9271_device *dev, u8 addr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) 	ret = max9271_write(dev, 0x00, addr << 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) 		dev_err(&dev->client->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) 			"MAX9271 I2C address change failed (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) EXPORT_SYMBOL_GPL(max9271_set_address);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) int max9271_set_deserializer_address(struct max9271_device *dev, u8 addr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 	ret = max9271_write(dev, 0x01, addr << 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 		dev_err(&dev->client->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 			"MAX9271 deserializer address set failed (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) EXPORT_SYMBOL_GPL(max9271_set_deserializer_address);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) int max9271_set_translation(struct max9271_device *dev, u8 source, u8 dest)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) 	ret = max9271_write(dev, 0x09, source << 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) 		dev_err(&dev->client->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) 			"MAX9271 I2C translation setup failed (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) 	ret = max9271_write(dev, 0x0a, dest << 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) 	if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) 		dev_err(&dev->client->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 			"MAX9271 I2C translation setup failed (%d)\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) 	usleep_range(3500, 5000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) EXPORT_SYMBOL_GPL(max9271_set_translation);