162306a36Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0-only 262306a36Sopenharmony_ci/* 362306a36Sopenharmony_ci * EEPROMs access control driver for display configuration EEPROMs 462306a36Sopenharmony_ci * on DigsyMTC board. 562306a36Sopenharmony_ci * 662306a36Sopenharmony_ci * (C) 2011 DENX Software Engineering, Anatolij Gustschin <agust@denx.de> 762306a36Sopenharmony_ci * 862306a36Sopenharmony_ci * FIXME: this driver is used on a device-tree probed platform: it 962306a36Sopenharmony_ci * should be defined as a bit-banged SPI device and probed from the device 1062306a36Sopenharmony_ci * tree and not like this with static grabbing of a few numbered GPIO 1162306a36Sopenharmony_ci * lines at random. 1262306a36Sopenharmony_ci * 1362306a36Sopenharmony_ci * Add proper SPI and EEPROM in arch/powerpc/boot/dts/digsy_mtc.dts 1462306a36Sopenharmony_ci * and delete this driver. 1562306a36Sopenharmony_ci */ 1662306a36Sopenharmony_ci 1762306a36Sopenharmony_ci#include <linux/gpio.h> 1862306a36Sopenharmony_ci#include <linux/gpio/machine.h> 1962306a36Sopenharmony_ci#include <linux/init.h> 2062306a36Sopenharmony_ci#include <linux/platform_device.h> 2162306a36Sopenharmony_ci#include <linux/spi/spi.h> 2262306a36Sopenharmony_ci#include <linux/spi/spi_gpio.h> 2362306a36Sopenharmony_ci#include <linux/eeprom_93xx46.h> 2462306a36Sopenharmony_ci 2562306a36Sopenharmony_ci#define GPIO_EEPROM_CLK 216 2662306a36Sopenharmony_ci#define GPIO_EEPROM_CS 210 2762306a36Sopenharmony_ci#define GPIO_EEPROM_DI 217 2862306a36Sopenharmony_ci#define GPIO_EEPROM_DO 249 2962306a36Sopenharmony_ci#define GPIO_EEPROM_OE 255 3062306a36Sopenharmony_ci#define EE_SPI_BUS_NUM 1 3162306a36Sopenharmony_ci 3262306a36Sopenharmony_cistatic void digsy_mtc_op_prepare(void *p) 3362306a36Sopenharmony_ci{ 3462306a36Sopenharmony_ci /* enable */ 3562306a36Sopenharmony_ci gpio_set_value(GPIO_EEPROM_OE, 0); 3662306a36Sopenharmony_ci} 3762306a36Sopenharmony_ci 3862306a36Sopenharmony_cistatic void digsy_mtc_op_finish(void *p) 3962306a36Sopenharmony_ci{ 4062306a36Sopenharmony_ci /* disable */ 4162306a36Sopenharmony_ci gpio_set_value(GPIO_EEPROM_OE, 1); 4262306a36Sopenharmony_ci} 4362306a36Sopenharmony_ci 4462306a36Sopenharmony_cistruct eeprom_93xx46_platform_data digsy_mtc_eeprom_data = { 4562306a36Sopenharmony_ci .flags = EE_ADDR8, 4662306a36Sopenharmony_ci .prepare = digsy_mtc_op_prepare, 4762306a36Sopenharmony_ci .finish = digsy_mtc_op_finish, 4862306a36Sopenharmony_ci}; 4962306a36Sopenharmony_ci 5062306a36Sopenharmony_cistatic struct spi_gpio_platform_data eeprom_spi_gpio_data = { 5162306a36Sopenharmony_ci .num_chipselect = 1, 5262306a36Sopenharmony_ci}; 5362306a36Sopenharmony_ci 5462306a36Sopenharmony_cistatic struct platform_device digsy_mtc_eeprom = { 5562306a36Sopenharmony_ci .name = "spi_gpio", 5662306a36Sopenharmony_ci .id = EE_SPI_BUS_NUM, 5762306a36Sopenharmony_ci .dev = { 5862306a36Sopenharmony_ci .platform_data = &eeprom_spi_gpio_data, 5962306a36Sopenharmony_ci }, 6062306a36Sopenharmony_ci}; 6162306a36Sopenharmony_ci 6262306a36Sopenharmony_cistatic struct gpiod_lookup_table eeprom_spi_gpiod_table = { 6362306a36Sopenharmony_ci .dev_id = "spi_gpio", 6462306a36Sopenharmony_ci .table = { 6562306a36Sopenharmony_ci GPIO_LOOKUP("gpio@b00", GPIO_EEPROM_CLK, 6662306a36Sopenharmony_ci "sck", GPIO_ACTIVE_HIGH), 6762306a36Sopenharmony_ci GPIO_LOOKUP("gpio@b00", GPIO_EEPROM_DI, 6862306a36Sopenharmony_ci "mosi", GPIO_ACTIVE_HIGH), 6962306a36Sopenharmony_ci GPIO_LOOKUP("gpio@b00", GPIO_EEPROM_DO, 7062306a36Sopenharmony_ci "miso", GPIO_ACTIVE_HIGH), 7162306a36Sopenharmony_ci GPIO_LOOKUP("gpio@b00", GPIO_EEPROM_CS, 7262306a36Sopenharmony_ci "cs", GPIO_ACTIVE_HIGH), 7362306a36Sopenharmony_ci { }, 7462306a36Sopenharmony_ci }, 7562306a36Sopenharmony_ci}; 7662306a36Sopenharmony_ci 7762306a36Sopenharmony_cistatic struct spi_board_info digsy_mtc_eeprom_info[] __initdata = { 7862306a36Sopenharmony_ci { 7962306a36Sopenharmony_ci .modalias = "93xx46", 8062306a36Sopenharmony_ci .max_speed_hz = 1000000, 8162306a36Sopenharmony_ci .bus_num = EE_SPI_BUS_NUM, 8262306a36Sopenharmony_ci .chip_select = 0, 8362306a36Sopenharmony_ci .mode = SPI_MODE_0, 8462306a36Sopenharmony_ci .platform_data = &digsy_mtc_eeprom_data, 8562306a36Sopenharmony_ci }, 8662306a36Sopenharmony_ci}; 8762306a36Sopenharmony_ci 8862306a36Sopenharmony_cistatic int __init digsy_mtc_eeprom_devices_init(void) 8962306a36Sopenharmony_ci{ 9062306a36Sopenharmony_ci int ret; 9162306a36Sopenharmony_ci 9262306a36Sopenharmony_ci ret = gpio_request_one(GPIO_EEPROM_OE, GPIOF_OUT_INIT_HIGH, 9362306a36Sopenharmony_ci "93xx46 EEPROMs OE"); 9462306a36Sopenharmony_ci if (ret) { 9562306a36Sopenharmony_ci pr_err("can't request gpio %d\n", GPIO_EEPROM_OE); 9662306a36Sopenharmony_ci return ret; 9762306a36Sopenharmony_ci } 9862306a36Sopenharmony_ci gpiod_add_lookup_table(&eeprom_spi_gpiod_table); 9962306a36Sopenharmony_ci spi_register_board_info(digsy_mtc_eeprom_info, 10062306a36Sopenharmony_ci ARRAY_SIZE(digsy_mtc_eeprom_info)); 10162306a36Sopenharmony_ci return platform_device_register(&digsy_mtc_eeprom); 10262306a36Sopenharmony_ci} 10362306a36Sopenharmony_cidevice_initcall(digsy_mtc_eeprom_devices_init); 104