}
if (clk->flags & CLOCK_NO_IDLE_PARENT)
-- omap1_clk_deny_idle(clk->parent);
++ if (!cpu_is_omap24xx())
++ omap1_clk_deny_idle(clk->parent);
}
ret = clk->enable(clk);
if (likely(clk->parent)) {
omap1_clk_disable(clk->parent);
if (clk->flags & CLOCK_NO_IDLE_PARENT)
-- omap1_clk_allow_idle(clk->parent);
++ if (!cpu_is_omap24xx())
++ omap1_clk_allow_idle(clk->parent);
}
}
}
if (unlikely(clk->enable_reg == 0)) {
printk(KERN_ERR "clock.c: Enable for %s without enable code\n",
clk->name);
-- return -EINVAL;
++ return 0;
}
if (clk->flags & ENABLE_REG_32BIT) {
int crystal_type = 0; /* Default 12 MHz */
u32 reg;
--#ifdef CONFIG_DEBUG_LL
-- /* Resets some clocks that may be left on from bootloader,
- * but leaves serial clocks on.
- * but leaves serial clocks on.
-- */
-- omap_writel(0x3 << 29, MOD_CONF_CTRL_0);
--#endif
--
/* USB_REQ_EN will be disabled later if necessary (usb_dc_ck) */
reg = omap_readw(SOFT_REQ_REG) & (1 << 4);
omap_writew(reg, SOFT_REQ_REG);
-- if (!cpu_is_omap15xx())
-- omap_writew(0, SOFT_REQ_REG2);
++ omap_writew(0, SOFT_REQ_REG2);
clk_init(&omap1_clk_functions);
info = omap_get_config(OMAP_TAG_CLOCK, struct omap_clock_config);
if (info != NULL) {
-- if (!cpu_is_omap15xx())
++ if (!cpu_is_omap1510())
crystal_type = info->system_clock_type;
}
#include <linux/delay.h>
#include <linux/workqueue.h>
#include <linux/input.h>
--#include <linux/err.h>
--#include <linux/clk.h>
- #include <linux/delay.h>
#include <asm/hardware.h>
#include <asm/mach-types.h>
#include <asm/arch/keypad.h>
#include <asm/arch/menelaus.h>
#include <asm/arch/dma.h>
--#include <asm/arch/gpmc.h>
#include "prcm-regs.h"
#include <asm/io.h>
--
--#define H4_FLASH_CS 0
--#define H4_SMC91X_CS 1
++#include <asm/delay.h>
static unsigned int row_gpios[6] = { 88, 89, 124, 11, 6, 96 };
static unsigned int col_gpios[7] = { 90, 91, 100, 36, 12, 97, 98 };
};
static struct resource h4_flash_resource = {
++ .start = H4_CS0_BASE,
++ .end = H4_CS0_BASE + SZ_64M - 1,
.flags = IORESOURCE_MEM,
};
.resource = &h4_flash_resource,
};
++static struct resource h4_smc91x_resources[] = {
++ [0] = {
++ .start = OMAP24XX_ETHR_START, /* Physical */
++ .end = OMAP24XX_ETHR_START + 0xf,
++ .flags = IORESOURCE_MEM,
++ },
++ [1] = {
++ .start = OMAP_GPIO_IRQ(OMAP24XX_ETHR_GPIO_IRQ),
++ .end = OMAP_GPIO_IRQ(OMAP24XX_ETHR_GPIO_IRQ),
++ .flags = IORESOURCE_IRQ,
++ },
++};
++
++static struct platform_device h4_smc91x_device = {
++ .name = "smc91x",
++ .id = -1,
++ .num_resources = ARRAY_SIZE(h4_smc91x_resources),
++ .resource = h4_smc91x_resources,
++};
++
/* Select between the IrDA and aGPS module
*/
--#if defined(CONFIG_OMAP_IR) || defined(CONFIG_OMAP_IR_MODULE)
static int h4_select_irda(struct device *dev, int state)
{
unsigned char expa;
return err;
}
--static void set_trans_mode(struct work_struct *work)
++static void set_trans_mode(void *data)
{
-- struct omap_irda_config *irda_config =
-- container_of(work, struct omap_irda_config, gpio_expa.work);
-- int mode = irda_config->mode;
++ int *mode = data;
unsigned char expa;
int err = 0;
expa &= ~0x01;
-- if (!(mode & IR_SIRMODE)) { /* MIR/FIR */
++ if (!(*mode & IR_SIRMODE)) { /* MIR/FIR */
expa |= 0x01;
}
{
struct omap_irda_config *irda_config = dev->platform_data;
-- irda_config->mode = mode;
cancel_delayed_work(&irda_config->gpio_expa);
-- PREPARE_DELAYED_WORK(&irda_config->gpio_expa, set_trans_mode);
++ PREPARE_WORK(&irda_config->gpio_expa, set_trans_mode, &mode);
++#error this is not permitted - mode is an argument variable
schedule_delayed_work(&irda_config->gpio_expa, 0);
return 0;
}
--#else
--static int h4_select_irda(struct device *dev, int state) { return 0; }
--static int h4_transceiver_mode(struct device *dev, int mode) { return 0; }
--#endif
static struct omap_irda_config h4_irda_data = {
.transceiver_cap = IR_SIRMODE | IR_MIRMODE | IR_FIRMODE,
};
static struct platform_device *h4_devices[] __initdata = {
++ &h4_smc91x_device,
&h4_flash_device,
&h4_irda_device,
&h4_kp_device,
&h4_lcd_device,
};
--/* 2420 Sysboot setup (2430 is different) */
--static u32 get_sysboot_value(void)
--{
-- return (omap_readl(OMAP242X_CONTROL_STATUS) & 0xFFF);
--}
--
--/* FIXME: This function should be moved to some other file, gpmc.c? */
--
--/* H4-2420's always used muxed mode, H4-2422's always use non-muxed
-- *
-- * Note: OMAP-GIT doesn't correctly do is_cpu_omap2422 and is_cpu_omap2423
-- * correctly. The macro needs to look at production_id not just hawkeye.
-- */
--static u32 is_gpmc_muxed(void)
--{
-- u32 mux;
-- mux = get_sysboot_value();
-- if ((mux & 0xF) == 0xd)
-- return 1; /* NAND config (could be either) */
-- if (mux & 0x2) /* if mux'ed */
-- return 1;
-- else
-- return 0;
--}
--
--static inline void __init h4_init_debug(void)
++static inline void __init h4_init_smc91x(void)
{
-- int eth_cs;
-- unsigned long cs_mem_base;
-- unsigned int muxed, rate;
-- struct clk *l3ck;
--
-- eth_cs = H4_SMC91X_CS;
--
-- l3ck = clk_get(NULL, "core_l3_ck");
-- if (IS_ERR(l3ck))
-- rate = 100000000;
-- else
-- rate = clk_get_rate(l3ck);
--
-- if (is_gpmc_muxed())
-- muxed = 0x200;
-- else
-- muxed = 0;
--
/* Make sure CS1 timings are correct */
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG1,
-- 0x00011000 | muxed);
--
-- if (rate >= 160000000) {
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG2, 0x001f1f01);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG3, 0x00080803);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG4, 0x1c0b1c0a);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG5, 0x041f1F1F);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG6, 0x000004C4);
-- } else if (rate >= 130000000) {
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG2, 0x001f1f00);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG3, 0x00080802);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG4, 0x1C091C09);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG5, 0x041f1F1F);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG6, 0x000004C4);
-- } else {/* rate = 100000000 */
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG2, 0x001f1f00);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG3, 0x00080802);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG4, 0x1C091C09);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG5, 0x031A1F1F);
-- gpmc_cs_write_reg(eth_cs, GPMC_CS_CONFIG6, 0x000003C2);
-- }
--
-- if (gpmc_cs_request(eth_cs, SZ_16M, &cs_mem_base) < 0) {
-- printk(KERN_ERR "Failed to request GPMC mem for smc91x\n");
-- return;
-- }
--
++ GPMC_CONFIG1_1 = 0x00011200;
++ GPMC_CONFIG2_1 = 0x001f1f01;
++ GPMC_CONFIG3_1 = 0x00080803;
++ GPMC_CONFIG4_1 = 0x1c091c09;
++ GPMC_CONFIG5_1 = 0x041f1f1f;
++ GPMC_CONFIG6_1 = 0x000004c4;
++ GPMC_CONFIG7_1 = 0x00000f40 | (0x08000000 >> 24);
udelay(100);
omap_cfg_reg(M15_24XX_GPIO92);
-- if (debug_card_init(cs_mem_base, OMAP24XX_ETHR_GPIO_IRQ) < 0)
-- gpmc_cs_free(eth_cs);
--}
--
--static void __init h4_init_flash(void)
--{
-- unsigned long base;
--
-- if (gpmc_cs_request(H4_FLASH_CS, SZ_64M, &base) < 0) {
-- printk("Can't request GPMC CS for flash\n");
++ if (omap_request_gpio(OMAP24XX_ETHR_GPIO_IRQ) < 0) {
++ printk(KERN_ERR "Failed to request GPIO%d for smc91x IRQ\n",
++ OMAP24XX_ETHR_GPIO_IRQ);
return;
}
-- h4_flash_resource.start = base;
-- h4_flash_resource.end = base + SZ_64M - 1;
++ omap_set_gpio_direction(OMAP24XX_ETHR_GPIO_IRQ, 1);
}
static void __init omap_h4_init_irq(void)
omap2_init_common_hw();
omap_init_irq();
omap_gpio_init();
-- h4_init_flash();
++ h4_init_smc91x();
}
static struct omap_uart_config h4_uart_config __initdata = {
--#ifdef CONFIG_MACH_OMAP2_H4_USB1
-- .enabled_uarts = ((1 << 0) | (1 << 1)),
--#else
.enabled_uarts = ((1 << 0) | (1 << 1) | (1 << 2)),
--#endif
};
static struct omap_mmc_config h4_mmc_config __initdata = {
.ctrl_name = "internal",
};
--static struct omap_usb_config h4_usb_config __initdata = {
--#ifdef CONFIG_MACH_OMAP2_H4_USB1
-- /* NOTE: usb1 could also be used with 3 wire signaling */
-- .pins[1] = 4,
--#endif
--
--#ifdef CONFIG_MACH_OMAP_H4_OTG
-- /* S1.10 ON -- USB OTG port
-- * usb0 switched to Mini-AB port and isp1301 transceiver;
-- * S2.POS3 = OFF, S2.POS4 = ON ... to allow battery charging
-- */
-- .otg = 1,
-- .pins[0] = 4,
--#ifdef CONFIG_USB_GADGET_OMAP
-- /* use OTG cable, or standard A-to-MiniB */
-- .hmc_mode = 0x14, /* 0:dev/otg 1:host 2:disable */
--#elif defined(CONFIG_USB_OHCI_HCD) || defined(CONFIG_USB_OHCI_HCD_MODULE)
-- /* use OTG cable, or NONSTANDARD (B-to-MiniB) */
-- .hmc_mode = 0x11, /* 0:host 1:host 2:disable */
--#endif /* XX */
--
--#else
-- /* S1.10 OFF -- usb "download port"
-- * usb0 switched to Mini-B port and isp1105 transceiver;
-- * S2.POS3 = ON, S2.POS4 = OFF ... to enable battery charging
-- */
-- .register_dev = 1,
-- .pins[0] = 3,
--// .hmc_mode = 0x14, /* 0:dev 1:host 2:disable */
-- .hmc_mode = 0x00, /* 0:dev|otg 1:disable 2:disable */
--#endif
--};
--
static struct omap_board_config_kernel h4_config[] = {
{ OMAP_TAG_UART, &h4_uart_config },
{ OMAP_TAG_MMC, &h4_mmc_config },
{ OMAP_TAG_LCD, &h4_lcd_config },
-- { OMAP_TAG_USB, &h4_usb_config },
--};
--
--#ifdef CONFIG_MACH_OMAP_H4_TUSB
--
--#include <linux/usb/musb.h>
--
--static struct musb_hdrc_platform_data tusb_data = {
-- .mode = MUSB_OTG,
-- .min_power = 25, /* x2 = 50 mA drawn from VBUS as peripheral */
--
-- /* 1.8V supplied by Menelaus, other voltages supplied by VBAT;
-- * so no switching.
-- */
};
--static void __init tusb_evm_setup(void)
--{
-- static char announce[] __initdata =
-- KERN_INFO "TUSB 6010 EVM\n";
-- int irq;
-- unsigned dmachan = 0;
--
-- /* There are at least 32 different combinations of boards that
-- * are loosely called "H4", with a 2420 ... different OMAP chip
-- * revisions (with pin mux changes for DMAREQ, GPMC errata, etc),
-- * modifications of the CPU board, mainboard, EVM, TUSB etc.
-- * Plus omap2422, omap2423, etc.
-- *
-- * So you might need to tweak this setup to make the TUSB EVM
-- * behave on your particular setup ...
-- */
--
-- /* Already set up: GPMC AD[0..15], CLK, nOE, nWE, nADV_ALE */
-- omap_cfg_reg(E2_GPMC_NCS2);
-- omap_cfg_reg(L2_GPMC_NCS7);
-- omap_cfg_reg(M1_GPMC_WAIT2);
--
-- switch ((system_rev >> 8) & 0x0f) {
-- case 0: /* ES 1.0 */
-- case 1: /* ES 2.0 */
-- /* Assume early board revision without optional ES2.0
-- * rework to swap J15 & AA10 so DMAREQ0 works
-- */
-- omap_cfg_reg(AA10_242X_GPIO13);
-- irq = 13;
-- // omap_cfg_reg(J15_24XX_DMAREQ0);
-- break;
-- default:
-- /* Later Menelaus boards can support all 6 DMA request
-- * lines, at the price of boot flash A23-A26.
-- */
-- omap_cfg_reg(J15_24XX_GPIO99);
-- irq = 99;
-- dmachan = (1 << 1) | (1 << 0);
--#if !(defined(CONFIG_MTD_OMAP_NOR) || defined(CONFIG_MTD_OMAP_NOR_MODULE))
-- dmachan |= (1 << 5) | (1 << 4) (1 << 3) | (1 << 2);
--#endif
-- break;
-- }
--
-- if (tusb6010_setup_interface(&tusb_data,
-- TUSB6010_REFCLK_24, /* waitpin */ 2,
-- /* async cs */ 2, /* sync cs */ 7,
-- irq, dmachan) == 0)
-- printk(announce);
--}
--
--#endif
--
static void __init omap_h4_init(void)
{
/*
}
#endif
--#ifdef CONFIG_MACH_OMAP2_H4_USB1
-- /* S3.3 controls whether these pins are for UART2 or USB1 */
-- omap_cfg_reg(N14_24XX_USB1_SE0);
-- omap_cfg_reg(P15_24XX_USB1_DAT);
-- omap_cfg_reg(W20_24XX_USB1_TXEN);
-- omap_cfg_reg(V19_24XX_USB1_RCV);
--#endif
--
platform_add_devices(h4_devices, ARRAY_SIZE(h4_devices));
omap_board_config = h4_config;
omap_board_config_size = ARRAY_SIZE(h4_config);
omap_serial_init();
--
-- /* smc91x, debug leds, ps/2, extra uarts */
-- h4_init_debug();
--
--#ifdef CONFIG_MACH_OMAP_H4_TUSB
-- tusb_evm_setup();
--#endif
--
}
static void __init omap_h4_map_io(void)
oprofile-y := $(DRIVER_OBJS) common.o backtrace.o
oprofile-$(CONFIG_CPU_XSCALE) += op_model_xscale.o
- oprofile-$(CONFIG_CPU_V6) += op_model_v6.o
-oprofile-$(CONFIG_OPROFILE_ARM11_CORE) += op_model_arm11_core.o
-oprofile-$(CONFIG_OPROFILE_ARMV6) += op_model_v6.o
-oprofile-$(CONFIG_OPROFILE_MPCORE) += op_model_mpcore.o
+
spec = &op_xscale_spec;
#endif
- #ifdef CONFIG_CPU_V6
- spec = &op_arm11_spec;
-#ifdef CONFIG_OPROFILE_ARMV6
- spec = &op_armv6_spec;
-#endif
-
-#ifdef CONFIG_OPROFILE_MPCORE
- spec = &op_mpcore_spec;
--#endif
--
if (spec) {
ret = spec->init();
if (ret < 0)
extern struct op_arm_model_spec op_xscale_spec;
#endif
- #ifdef CONFIG_CPU_V6
- extern struct op_arm_model_spec op_arm11_spec;
- #endif
-extern struct op_arm_model_spec op_armv6_spec;
-extern struct op_arm_model_spec op_mpcore_spec;
--
extern void arm_backtrace(struct pt_regs * const regs, unsigned int depth);
extern int __init op_arm_init(struct oprofile_operations *ops, struct op_arm_model_spec *spec);
source "drivers/dma/Kconfig"
+ source "drivers/auxdisplay/Kconfig"
+
source "drivers/kvm/Kconfig"
+source "drivers/ssi/Kconfig"
+
endmenu
obj-$(CONFIG_FB_I810) += video/i810/
obj-$(CONFIG_FB_INTEL) += video/intelfb/
+# we also need input/serio early so serio bus is initialized by the time
+# serial drivers start registering their serio ports
+obj-$(CONFIG_SERIO) += input/serio/
obj-y += serial/
obj-$(CONFIG_PARPORT) += parport/
-obj-y += base/ block/ misc/ mfd/ net/ media/ cbus/
+obj-y += base/ block/ misc/ mfd/ net/ media/
+obj-$(CONFIG_I2C) += i2c/
+obj-y += media/ ssi/ cbus/
obj-$(CONFIG_NUBUS) += nubus/
obj-$(CONFIG_ATM) += atm/
- obj-$(CONFIG_PPC_PMAC) += macintosh/
+ obj-y += macintosh/
obj-$(CONFIG_IDE) += ide/
obj-$(CONFIG_FC4) += fc4/
obj-$(CONFIG_SCSI) += scsi/
obj-$(CONFIG_KEYBOARD_SPITZ) += spitzkbd.o
obj-$(CONFIG_KEYBOARD_HIL) += hil_kbd.o
obj-$(CONFIG_KEYBOARD_HIL_OLD) += hilkbd.o
-obj-$(CONFIG_KEYBOARD_OMAP) += omap-keypad.o
-obj-$(CONFIG_KEYBOARD_AAED2000) += aaed2000_kbd.o
+obj-$(CONFIG_KEYBOARD_OMAP) += omap-keypad.o
+obj-$(CONFIG_OMAP_PS2) += innovator_ps2.o
+obj-$(CONFIG_KEYBOARD_AAED2000) += aaed2000_kbd.o
+ obj-$(CONFIG_KEYBOARD_GPIO) += gpio_keys.o
if INPUT_TOUCHSCREEN
config TOUCHSCREEN_ADS7846
- tristate "ADS 7846/7843 based touchscreens"
+ tristate "ADS 7846 based touchscreens"
depends on SPI_MASTER
- select HWMON
- depends on HWMON = n || HWMON
help
Say Y here if you have a touchscreen interface using the
- ADS7846 or ADS7843 controller, and your board-specific setup
+ ADS7846 controller, and your board-specific initialization
- code includes that in its table of SPI devices. You will
- also get hwmon interfaces for the temperature and voltage
- sensors this chip provides.
+ code includes that in its table of SPI devices.
- If HWMON is selected, and the driver is told the reference voltage
- on your board, you will also get hwmon interfaces for the voltage
- (and on ads7846, temperature) sensors of this chip.
-
If unsure, say N (but it's safe to say "Y").
To compile this driver as a module, choose M here: the
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
--#include <linux/hwmon.h>
++#include <linux/device.h>
#include <linux/init.h>
--#include <linux/err.h>
#include <linux/delay.h>
#include <linux/input.h>
#include <linux/interrupt.h>
* files.
*/
--#define TS_POLL_DELAY (1 * 1000000) /* ns delay before the first sample */
- #define TS_POLL_PERIOD (5 * 1000000) /* ns delay between samples */
-#define TS_POLL_PERIOD (5 * 1000000) /* ns delay between samples */
++#define TS_POLL_PERIOD msecs_to_jiffies(10)
/* this driver doesn't aim at the peak continuous sample rate */
#define SAMPLE_BITS (8 /*cmd*/ + 16 /*sample*/ + 2 /* before, after */)
char phys[32];
struct spi_device *spi;
- struct class_device *hwmon;
-
-#if defined(CONFIG_HWMON) || defined(CONFIG_HWMON_MODULE)
+ struct attribute_group *attr_group;
- struct class_device *hwmon;
-#endif
-
u16 model;
u16 vref_delay_usecs;
u16 x_plate_ohms;
u16 debounce_rep;
spinlock_t lock;
-- struct hrtimer timer;
++ struct timer_list timer; /* P: lock */
unsigned pendown:1; /* P: lock */
unsigned pending:1; /* P: lock */
// FIXME remove "irq_disabled"
unsigned irq_disabled:1; /* P: lock */
unsigned disabled:1;
-- int (*filter)(void *data, int data_idx, int *val);
-- void *filter_data;
-- void (*filter_cleanup)(void *data);
int (*get_pendown_state)(void);
};
#define MAX_12BIT ((1<<12)-1)
/* leave ADC powered up (disables penirq) between differential samples */
--#define READ_12BIT_DFR(x, adc, vref) (ADS_START | ADS_A2A1A0_d_ ## x \
-- | ADS_12_BIT | ADS_DFR | \
-- (adc ? ADS_PD10_ADC_ON : 0) | (vref ? ADS_PD10_REF_ON : 0))
++#define READ_12BIT_DFR(x) (ADS_START | ADS_A2A1A0_d_ ## x \
++ | ADS_12_BIT | ADS_DFR)
--#define READ_Y(vref) (READ_12BIT_DFR(y, 1, vref))
--#define READ_Z1(vref) (READ_12BIT_DFR(z1, 1, vref))
--#define READ_Z2(vref) (READ_12BIT_DFR(z2, 1, vref))
++#define READ_Y (READ_12BIT_DFR(y) | ADS_PD10_ADC_ON)
++#define READ_Z1 (READ_12BIT_DFR(z1) | ADS_PD10_ADC_ON)
++#define READ_Z2 (READ_12BIT_DFR(z2) | ADS_PD10_ADC_ON)
--#define READ_X(vref) (READ_12BIT_DFR(x, 1, vref))
--#define PWRDOWN (READ_12BIT_DFR(y, 0, 0)) /* LAST */
++#define READ_X (READ_12BIT_DFR(x) | ADS_PD10_ADC_ON)
++#define PWRDOWN (READ_12BIT_DFR(y) | ADS_PD10_PDOWN) /* LAST */
/* single-ended samples need to first power up reference voltage;
* we leave both ADC and VREF powered
#define READ_12BIT_SER(x) (ADS_START | ADS_A2A1A0_ ## x \
| ADS_12_BIT | ADS_SER)
--#define REF_ON (READ_12BIT_DFR(x, 1, 1))
--#define REF_OFF (READ_12BIT_DFR(y, 0, 0))
++#define REF_ON (READ_12BIT_DFR(x) | ADS_PD10_ALL_ON)
++#define REF_OFF (READ_12BIT_DFR(y) | ADS_PD10_PDOWN)
/*--------------------------------------------------------------------------*/
/*
* Non-touchscreen sensors only use single-ended conversions.
-- * The range is GND..vREF. The ads7843 and ads7835 must use external vREF;
-- * ads7846 lets that pin be unconnected, to use internal vREF.
- *
- * FIXME make external vREF_mV be a module option, and use that as needed...
*/
- static const unsigned vREF_mV = 2500;
-static unsigned vREF_mV;
-module_param(vREF_mV, uint, 0);
-MODULE_PARM_DESC(vREF_mV, "external vREF voltage, in milliVolts");
struct ser_req {
u8 ref_on;
struct ser_req *req = kzalloc(sizeof *req, GFP_KERNEL);
int status;
int sample;
-- int use_internal;
++ int i;
if (!req)
return -ENOMEM;
spi_message_init(&req->msg);
-- /* FIXME boards with ads7846 might use external vref instead ... */
-- use_internal = (ts->model == 7846);
--
-- /* maybe turn on internal vREF, and let it settle */
-- if (use_internal) {
-- req->ref_on = REF_ON;
-- req->xfer[0].tx_buf = &req->ref_on;
-- req->xfer[0].len = 1;
-- spi_message_add_tail(&req->xfer[0], &req->msg);
--
-- req->xfer[1].rx_buf = &req->scratch;
-- req->xfer[1].len = 2;
--
-- /* for 1uF, settle for 800 usec; no cap, 100 usec. */
-- req->xfer[1].delay_usecs = ts->vref_delay_usecs;
-- spi_message_add_tail(&req->xfer[1], &req->msg);
-- }
++ /* activate reference, so it has time to settle; */
++ req->ref_on = REF_ON;
++ req->xfer[0].tx_buf = &req->ref_on;
++ req->xfer[0].len = 1;
++ req->xfer[1].rx_buf = &req->scratch;
++ req->xfer[1].len = 2;
++
++ /*
++ * for external VREF, 0 usec (and assume it's always on);
++ * for 1uF, use 800 usec;
++ * no cap, 100 usec.
++ */
++ req->xfer[1].delay_usecs = ts->vref_delay_usecs;
/* take sample */
req->command = (u8) command;
req->xfer[2].tx_buf = &req->command;
req->xfer[2].len = 1;
-- spi_message_add_tail(&req->xfer[2], &req->msg);
--
req->xfer[3].rx_buf = &req->sample;
req->xfer[3].len = 2;
-- spi_message_add_tail(&req->xfer[3], &req->msg);
/* REVISIT: take a few more samples, and compare ... */
-- /* maybe off internal vREF */
-- if (use_internal) {
-- req->ref_off = REF_OFF;
-- req->xfer[4].tx_buf = &req->ref_off;
-- req->xfer[4].len = 1;
-- spi_message_add_tail(&req->xfer[4], &req->msg);
--
-- req->xfer[5].rx_buf = &req->scratch;
-- req->xfer[5].len = 2;
-- CS_CHANGE(req->xfer[5]);
-- spi_message_add_tail(&req->xfer[5], &req->msg);
-- }
++ /* turn off reference */
++ req->ref_off = REF_OFF;
++ req->xfer[4].tx_buf = &req->ref_off;
++ req->xfer[4].len = 1;
++ req->xfer[5].rx_buf = &req->scratch;
++ req->xfer[5].len = 2;
++
++ CS_CHANGE(req->xfer[5]);
++
++ /* group all the transfers together, so we can't interfere with
++ * reading touchscreen state; disable penirq while sampling
++ */
++ for (i = 0; i < 6; i++)
++ spi_message_add_tail(&req->xfer[i], &req->msg);
ts->irq_disabled = 1;
disable_irq(spi->irq);
return status ? status : sample;
}
- #define SHOW(name,var,adjust) static ssize_t \
-#if defined(CONFIG_HWMON) || defined(CONFIG_HWMON_MODULE)
-
-#define SHOW(name, var, adjust) static ssize_t \
++#define SHOW(name) static ssize_t \
name ## _show(struct device *dev, struct device_attribute *attr, char *buf) \
{ \
-- struct ads7846 *ts = dev_get_drvdata(dev); \
ssize_t v = ads7846_read12_ser(dev, \
-- READ_12BIT_SER(var) | ADS_PD10_ALL_ON); \
++ READ_12BIT_SER(name) | ADS_PD10_ALL_ON); \
if (v < 0) \
return v; \
-- return sprintf(buf, "%u\n", adjust(ts, v)); \
++ return sprintf(buf, "%u\n", (unsigned) v); \
} \
static DEVICE_ATTR(name, S_IRUGO, name ## _show, NULL);
--
--/* Sysfs conventions report temperatures in millidegrees Celcius.
- * We could use the low-accuracy two-sample scheme, but can't do the high
- * ADS7846 could use the low-accuracy two-sample scheme, but can't do the high
-- * accuracy scheme without calibration data. For now we won't try either;
- * userspace sees raw sensor values, and must scale appropriately.
- * userspace sees raw sensor values, and must scale/calibrate appropriately.
-- */
--static inline unsigned null_adjust(struct ads7846 *ts, ssize_t v)
--{
-- return v;
--}
--
- SHOW(temp0, temp0, null_adjust) // temp1_input
- SHOW(temp1, temp1, null_adjust) // temp2_input
-SHOW(temp0, temp0, null_adjust) /* temp1_input */
-SHOW(temp1, temp1, null_adjust) /* temp2_input */
--
--
--/* sysfs conventions report voltages in millivolts. We can convert voltages
-- * if we know vREF. userspace may need to scale vAUX to match the board's
-- * external resistors; we assume that vBATT only uses the internal ones.
-- */
--static inline unsigned vaux_adjust(struct ads7846 *ts, ssize_t v)
--{
-- unsigned retval = v;
--
-- /* external resistors may scale vAUX into 0..vREF */
-- retval *= vREF_mV;
-- retval = retval >> 12;
-- return retval;
--}
--
--static inline unsigned vbatt_adjust(struct ads7846 *ts, ssize_t v)
--{
-- unsigned retval = vaux_adjust(ts, v);
--
-- /* ads7846 has a resistor ladder to scale this signal down */
-- if (ts->model == 7846)
-- retval *= 4;
-- return retval;
--}
--
--SHOW(in0_input, vaux, vaux_adjust)
--SHOW(in1_input, vbatt, vbatt_adjust)
-
-
-static struct attribute *ads7846_attributes[] = {
- &dev_attr_temp0.attr,
- &dev_attr_temp1.attr,
- &dev_attr_in0_input.attr,
- &dev_attr_in1_input.attr,
- NULL,
-};
-
-static struct attribute_group ads7846_attr_group = {
- .attrs = ads7846_attributes,
-};
-
-static struct attribute *ads7843_attributes[] = {
- &dev_attr_in0_input.attr,
- &dev_attr_in1_input.attr,
- NULL,
-};
-
-static struct attribute_group ads7843_attr_group = {
- .attrs = ads7843_attributes,
-};
-
-static struct attribute *ads7845_attributes[] = {
- &dev_attr_in0_input.attr,
- NULL,
-};
-
-static struct attribute_group ads7845_attr_group = {
- .attrs = ads7845_attributes,
-};
-
-static int ads784x_hwmon_register(struct spi_device *spi, struct ads7846 *ts)
-{
- struct class_device *hwmon;
- int err;
-
- /* hwmon sensors need a reference voltage */
- switch (ts->model) {
- case 7846:
- if (!vREF_mV) {
- dev_dbg(&spi->dev, "assuming 2.5V internal vREF\n");
- vREF_mV = 2500;
- }
- break;
- case 7845:
- case 7843:
- if (!vREF_mV) {
- dev_warn(&spi->dev,
- "external vREF for ADS%d not specified\n",
- ts->model);
- return 0;
- }
- break;
- }
-
- /* different chips have different sensor groups */
- switch (ts->model) {
- case 7846:
- ts->attr_group = &ads7846_attr_group;
- break;
- case 7845:
- ts->attr_group = &ads7845_attr_group;
- break;
- case 7843:
- ts->attr_group = &ads7843_attr_group;
- break;
- default:
- dev_dbg(&spi->dev, "ADS%d not recognized\n", ts->model);
- return 0;
- }
-
- err = sysfs_create_group(&spi->dev.kobj, ts->attr_group);
- if (err)
- return err;
-
- hwmon = hwmon_device_register(&spi->dev);
- if (IS_ERR(hwmon)) {
- sysfs_remove_group(&spi->dev.kobj, ts->attr_group);
- return PTR_ERR(hwmon);
- }
-
- ts->hwmon = hwmon;
- return 0;
-}
-
-static void ads784x_hwmon_unregister(struct spi_device *spi,
- struct ads7846 *ts)
-{
- if (ts->hwmon) {
- sysfs_remove_group(&spi->dev.kobj, ts->attr_group);
- hwmon_device_unregister(ts->hwmon);
- }
-}
-
-#else
-static inline int ads784x_hwmon_register(struct spi_device *spi,
- struct ads7846 *ts)
-{
- return 0;
-}
--
-static inline void ads784x_hwmon_unregister(struct spi_device *spi,
- struct ads7846 *ts)
-{
-}
-#endif
++SHOW(temp0)
++SHOW(temp1)
++SHOW(vaux)
++SHOW(vbatt)
static int is_pen_down(struct device *dev)
{
static DEVICE_ATTR(disable, 0664, ads7846_disable_show, ads7846_disable_store);
- /*--------------------------------------------------------------------------*/
-static struct attribute *ads784x_attributes[] = {
++static struct attribute *ads7846_attributes[] = {
++ &dev_attr_temp0.attr,
++ &dev_attr_temp1.attr,
++ &dev_attr_vbatt.attr,
++ &dev_attr_vaux.attr,
++ &dev_attr_pen_down.attr,
++ &dev_attr_disable.attr,
++ NULL,
++};
+
- static void ads7846_report_pen_state(struct ads7846 *ts, int down)
- {
- struct input_dev *input_dev = ts->input;
++static struct attribute_group ads7846_attr_group = {
++ .attrs = ads7846_attributes,
++};
+
- input_report_key(input_dev, BTN_TOUCH, down);
- if (!down)
- input_report_abs(input_dev, ABS_PRESSURE, 0);
- #ifdef VERBOSE
- pr_debug("%s: %s\n", ts->spi->dev.bus_id, down ? "DOWN" : "UP");
- #endif
- }
++/*
++ * ads7843/7845 don't have temperature sensors, and
++ * use the other sensors a bit differently too
++ */
+
- static void ads7846_report_pen_position(struct ads7846 *ts, int x, int y,
- int pressure)
- {
- struct input_dev *input_dev = ts->input;
++static struct attribute *ads7843_attributes[] = {
++ &dev_attr_vbatt.attr,
++ &dev_attr_vaux.attr,
+ &dev_attr_pen_down.attr,
+ &dev_attr_disable.attr,
+ NULL,
+ };
- input_report_abs(input_dev, ABS_X, x);
- input_report_abs(input_dev, ABS_Y, y);
- input_report_abs(input_dev, ABS_PRESSURE, pressure);
-static struct attribute_group ads784x_attr_group = {
- .attrs = ads784x_attributes,
++static struct attribute_group ads7843_attr_group = {
++ .attrs = ads7843_attributes,
++};
+
- #ifdef VERBOSE
- pr_debug("%s: %d/%d/%d\n", ts->spi->dev.bus_id, x, y, pressure);
- #endif
- }
++static struct attribute *ads7845_attributes[] = {
++ &dev_attr_vaux.attr,
++ &dev_attr_pen_down.attr,
++ &dev_attr_disable.attr,
++ NULL,
++};
+
- static void ads7846_sync_events(struct ads7846 *ts)
- {
- struct input_dev *input_dev = ts->input;
++static struct attribute_group ads7845_attr_group = {
++ .attrs = ads7845_attributes,
+ };
- input_sync(input_dev);
- }
+ /*--------------------------------------------------------------------------*/
/*
* PENIRQ only kicks the timer. The timer only reissues the SPI transfer,
static void ads7846_rx(void *ads)
{
struct ads7846 *ts = ads;
++ struct input_dev *input_dev = ts->input;
unsigned Rt;
++ unsigned sync = 0;
u16 x, y, z1, z2;
++ unsigned long flags;
- /* ads7846_rx_val() did in-place conversion (including byteswap) from
- * on-the-wire format as part of debouncing to get stable readings.
+ /* adjust: on-wire is a must-ignore bit, a BE12 value, then padding;
+ * built from two 8 bit values written msb-first.
*/
-- x = ts->tc.x;
-- y = ts->tc.y;
-- z1 = ts->tc.z1;
-- z2 = ts->tc.z2;
++ x = (be16_to_cpu(ts->tc.x) >> 3) & 0x0fff;
++ y = (be16_to_cpu(ts->tc.y) >> 3) & 0x0fff;
++ z1 = (be16_to_cpu(ts->tc.z1) >> 3) & 0x0fff;
++ z2 = (be16_to_cpu(ts->tc.z2) >> 3) & 0x0fff;
/* range filtering */
if (x == MAX_12BIT)
x = 0;
-- if (likely(x && z1)) {
++ if (likely(x && z1 && !device_suspended(&ts->spi->dev))) {
/* compute touch pressure resistance using equation #2 */
Rt = z2;
Rt -= z1;
Rt = 0;
/* Sample found inconsistent by debouncing or pressure is beyond
- * the maximum. Don't report it to user space, repeat at least
- * once more the measurement
- */
+ * the maximum. Don't report it to user space, repeat at least
+ * once more the measurement */
if (ts->tc.ignore || Rt > ts->pressure_max) {
--#ifdef VERBOSE
-- pr_debug("%s: ignored %d pressure %d\n",
-- ts->spi->dev.bus_id, ts->tc.ignore, Rt);
--#endif
-- hrtimer_start(&ts->timer, ktime_set(0, TS_POLL_PERIOD),
- HRTIMER_REL);
- HRTIMER_MODE_REL);
++ mod_timer(&ts->timer, jiffies + TS_POLL_PERIOD);
return;
}
-- /* NOTE: We can't rely on the pressure to determine the pen down
- * state. The pressure value can fluctuate for quite a while
- * after lifting the pen and in some cases may not even settle at
- * the expected value. The only safe way to check for the pen up
- * condition is in the timer by reading the pen IRQ state.
- * state, even this controller has a pressure sensor. The pressure
- * value can fluctuate for quite a while after lifting the pen and
- * in some cases may not even settle at the expected value.
++ /* NOTE: "pendown" is inferred from pressure; we don't rely on
++ * being able to check nPENIRQ status, or "friendly" trigger modes
++ * (both-edges is much better than just-falling or low-level).
+ *
- * The only safe way to check for the pen up condition is in the
- * timer by reading the pen signal state (it's a GPIO _and_ IRQ).
++ * REVISIT: some boards may require reading nPENIRQ; it's
++ * needed on 7843. and 7845 reads pressure differently...
++ *
++ * REVISIT: the touchscreen might not be connected; this code
++ * won't notice that, even if nPENIRQ never fires ...
*/
++ if (!ts->pendown && Rt != 0) {
++ input_report_key(input_dev, BTN_TOUCH, 1);
++ sync = 1;
++ } else if (ts->pendown && Rt == 0) {
++ input_report_key(input_dev, BTN_TOUCH, 0);
++ sync = 1;
++ }
++
if (Rt) {
- if (!ts->pendown) {
- ads7846_report_pen_state(ts, 1);
- ts->pendown = 1;
- }
- ads7846_report_pen_position(ts, x, y, Rt);
- ads7846_sync_events(ts);
- struct input_dev *input = ts->input;
++ input_report_abs(input_dev, ABS_X, x);
++ input_report_abs(input_dev, ABS_Y, y);
++ sync = 1;
++ }
+
- if (!ts->pendown) {
- input_report_key(input, BTN_TOUCH, 1);
- ts->pendown = 1;
-#ifdef VERBOSE
- dev_dbg(&ts->spi->dev, "DOWN\n");
-#endif
- }
- input_report_abs(input, ABS_X, x);
- input_report_abs(input, ABS_Y, y);
- input_report_abs(input, ABS_PRESSURE, Rt);
++ if (sync) {
++ input_report_abs(input_dev, ABS_PRESSURE, Rt);
++ input_sync(input_dev);
+ }
- hrtimer_start(&ts->timer, ktime_set(0, TS_POLL_PERIOD), HRTIMER_REL);
- input_sync(input);
-#ifdef VERBOSE
- dev_dbg(&ts->spi->dev, "%4d/%4d/%4d\n", x, y, Rt);
++#ifdef VERBOSE
++ if (Rt || ts->pendown)
++ pr_debug("%s: %d/%d/%d%s\n", ts->spi->dev.bus_id,
++ x, y, Rt, Rt ? "" : " UP");
+ #endif
- }
+
- hrtimer_start(&ts->timer, ktime_set(0, TS_POLL_PERIOD),
- HRTIMER_MODE_REL);
++ spin_lock_irqsave(&ts->lock, flags);
++
++ ts->pendown = (Rt != 0);
++ mod_timer(&ts->timer, jiffies + TS_POLL_PERIOD);
++
++ spin_unlock_irqrestore(&ts->lock, flags);
}
--static int ads7846_debounce(void *ads, int data_idx, int *val)
++static void ads7846_debounce(void *ads)
{
struct ads7846 *ts = ads;
++ struct spi_message *m;
++ struct spi_transfer *t;
++ int val;
++ int status;
-- if (!ts->read_cnt || (abs(ts->last_read - *val) > ts->debounce_tol)) {
-- /* Start over collecting consistent readings. */
-- ts->read_rep = 0;
++ m = &ts->msg[ts->msg_idx];
++ t = list_entry(m->transfers.prev, struct spi_transfer, transfer_list);
++ val = (be16_to_cpu(*(__be16 *)t->rx_buf) >> 3) & 0x0fff;
++ if (!ts->read_cnt || (abs(ts->last_read - val) > ts->debounce_tol)) {
/* Repeat it, if this was the first read or the read
* wasn't consistent enough. */
if (ts->read_cnt < ts->debounce_max) {
-- ts->last_read = *val;
++ ts->last_read = val;
ts->read_cnt++;
-- return ADS7846_FILTER_REPEAT;
} else {
/* Maximum number of debouncing reached and still
* not enough number of consistent readings. Abort
* the whole sample, repeat it in the next sampling
* period.
*/
++ ts->tc.ignore = 1;
ts->read_cnt = 0;
-- return ADS7846_FILTER_IGNORE;
++ /* Last message will contain ads7846_rx() as the
++ * completion function.
++ */
++ m = ts->last_msg;
}
++ /* Start over collecting consistent readings. */
++ ts->read_rep = 0;
} else {
if (++ts->read_rep > ts->debounce_rep) {
/* Got a good reading for this coordinate,
* go for the next one. */
++ ts->tc.ignore = 0;
++ ts->msg_idx++;
ts->read_cnt = 0;
ts->read_rep = 0;
-- return ADS7846_FILTER_OK;
-- } else {
++ m++;
++ } else
/* Read more values that are consistent. */
ts->read_cnt++;
-- return ADS7846_FILTER_REPEAT;
-- }
-- }
--}
--
--static int ads7846_no_filter(void *ads, int data_idx, int *val)
--{
-- return ADS7846_FILTER_OK;
--}
--
--static void ads7846_rx_val(void *ads)
--{
-- struct ads7846 *ts = ads;
-- struct spi_message *m;
-- struct spi_transfer *t;
-- u16 *rx_val;
-- int val;
-- int action;
-- int status;
--
-- m = &ts->msg[ts->msg_idx];
-- t = list_entry(m->transfers.prev, struct spi_transfer, transfer_list);
- rx_val = (u16 *)t->rx_buf;
- rx_val = t->rx_buf;
-
- /* adjust: on-wire is a must-ignore bit, a BE12 value, then padding;
- * built from two 8 bit values written msb-first.
- */
-- val = be16_to_cpu(*rx_val) >> 3;
--
-- action = ts->filter(ts->filter_data, ts->msg_idx, &val);
-- switch (action) {
-- case ADS7846_FILTER_REPEAT:
-- break;
-- case ADS7846_FILTER_IGNORE:
-- ts->tc.ignore = 1;
-- /* Last message will contain ads7846_rx() as the
-- * completion function.
-- */
-- m = ts->last_msg;
-- break;
-- case ADS7846_FILTER_OK:
-- *rx_val = val;
-- ts->tc.ignore = 0;
-- m = &ts->msg[++ts->msg_idx];
-- break;
-- default:
-- BUG();
}
status = spi_async(ts->spi, m);
if (status)
status);
}
- static int ads7846_timer(struct hrtimer *handle)
-static enum hrtimer_restart ads7846_timer(struct hrtimer *handle)
++static void ads7846_timer(unsigned long handle)
{
-- struct ads7846 *ts = container_of(handle, struct ads7846, timer);
++ struct ads7846 *ts = (void *)handle;
int status = 0;
spin_lock_irq(&ts->lock);
-- if (unlikely(!ts->get_pendown_state() ||
-- device_suspended(&ts->spi->dev))) {
-- if (ts->pendown) {
- ads7846_report_pen_state(ts, 0);
- ads7846_sync_events(ts);
- struct input_dev *input = ts->input;
-
- input_report_key(input, BTN_TOUCH, 0);
- input_report_abs(input, ABS_PRESSURE, 0);
- input_sync(input);
-
-- ts->pendown = 0;
-#ifdef VERBOSE
- dev_dbg(&ts->spi->dev, "UP\n");
-#endif
-- }
--
- /* measurment cycle ended */
++ if (unlikely(ts->msg_idx && !ts->pendown)) {
+ /* measurement cycle ended */
if (!device_suspended(&ts->spi->dev)) {
ts->irq_disabled = 0;
enable_irq(ts->spi->irq);
}
ts->pending = 0;
++ ts->msg_idx = 0;
} else {
/* pen is still down, continue with the measurement */
ts->msg_idx = 0;
}
spin_unlock_irq(&ts->lock);
-- return HRTIMER_NORESTART;
}
static irqreturn_t ads7846_irq(int irq, void *handle)
ts->irq_disabled = 1;
disable_irq(ts->spi->irq);
ts->pending = 1;
-- hrtimer_start(&ts->timer, ktime_set(0, TS_POLL_DELAY),
- HRTIMER_REL);
- HRTIMER_MODE_REL);
++ mod_timer(&ts->timer, jiffies);
}
}
spin_unlock_irqrestore(&ts->lock, flags);
struct ads7846_platform_data *pdata = spi->dev.platform_data;
struct spi_message *m;
struct spi_transfer *x;
-- int vref;
int err;
if (!spi->irq) {
return -EINVAL;
}
- /* We'd set the wordsize to 12 bits ... except that some controllers
- * will then treat the 8 bit command words as 12 bits (and drop the
- * four MSBs of the 12 bit result). Result: inputs must be shifted
- * to discard the four garbage LSBs. (Also, not all controllers can
- * support 12 bit words.)
+ /* We'd set TX wordsize 8 bits and RX wordsize to 13 bits ... except
+ * that even if the hardware can do that, the SPI controller driver
+ * may not. So we stick to very-portable 8 bit words, both RX and TX.
*/
- spi->mode = SPI_MODE_1;
- err = spi_setup(spi);
- if (err < 0)
- return err;
+ spi->bits_per_word = 8;
ts = kzalloc(sizeof(struct ads7846), GFP_KERNEL);
input_dev = input_allocate_device();
ts->spi = spi;
ts->input = input_dev;
- ts->hwmon = hwmon;
- hrtimer_init(&ts->timer, CLOCK_MONOTONIC, HRTIMER_REL);
- hrtimer_init(&ts->timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
++ init_timer(&ts->timer);
++ ts->timer.data = (unsigned long) ts;
ts->timer.function = ads7846_timer;
spin_lock_init(&ts->lock);
ts->vref_delay_usecs = pdata->vref_delay_usecs ? : 100;
ts->x_plate_ohms = pdata->x_plate_ohms ? : 400;
ts->pressure_max = pdata->pressure_max ? : ~0;
--
-- if (pdata->filter != NULL) {
-- if (pdata->filter_init != NULL) {
-- err = pdata->filter_init(pdata, &ts->filter_data);
-- if (err < 0)
-- goto err_free_mem;
-- }
-- ts->filter = pdata->filter;
-- ts->filter_cleanup = pdata->filter_cleanup;
-- } else if (pdata->debounce_max) {
++ if (pdata->debounce_max) {
ts->debounce_max = pdata->debounce_max;
-- if (ts->debounce_max < 2)
-- ts->debounce_max = 2;
ts->debounce_tol = pdata->debounce_tol;
ts->debounce_rep = pdata->debounce_rep;
-- ts->filter = ads7846_debounce;
-- ts->filter_data = ts;
++ if (ts->debounce_rep > ts->debounce_max + 1)
++ ts->debounce_rep = ts->debounce_max - 1;
} else
-- ts->filter = ads7846_no_filter;
++ ts->debounce_tol = ~0;
ts->get_pendown_state = pdata->get_pendown_state;
snprintf(ts->phys, sizeof(ts->phys), "%s/input0", spi->dev.bus_id);
input_set_abs_params(input_dev, ABS_PRESSURE,
pdata->pressure_min, pdata->pressure_max, 0, 0);
-- vref = pdata->keep_vref_on;
--
/* set up the transfers to read touchscreen state; this assumes we
* use formula #2 for pressure, not #3.
*/
spi_message_init(m);
/* y- still on; turn on only y+ (and ADC) */
-- ts->read_y = READ_Y(vref);
++ ts->read_y = READ_Y;
x->tx_buf = &ts->read_y;
x->len = 1;
spi_message_add_tail(x, m);
x->len = 2;
spi_message_add_tail(x, m);
-- m->complete = ads7846_rx_val;
++ m->complete = ads7846_debounce;
m->context = ts;
m++;
/* turn y- off, x+ on, then leave in lowpower */
x++;
-- ts->read_x = READ_X(vref);
++ ts->read_x = READ_X;
x->tx_buf = &ts->read_x;
x->len = 1;
spi_message_add_tail(x, m);
x->len = 2;
spi_message_add_tail(x, m);
-- m->complete = ads7846_rx_val;
++ m->complete = ads7846_debounce;
m->context = ts;
/* turn y+ off, x- on; we'll use formula #2 */
spi_message_init(m);
x++;
-- ts->read_z1 = READ_Z1(vref);
++ ts->read_z1 = READ_Z1;
x->tx_buf = &ts->read_z1;
x->len = 1;
spi_message_add_tail(x, m);
x->len = 2;
spi_message_add_tail(x, m);
-- m->complete = ads7846_rx_val;
++ m->complete = ads7846_debounce;
m->context = ts;
m++;
spi_message_init(m);
x++;
-- ts->read_z2 = READ_Z2(vref);
++ ts->read_z2 = READ_Z2;
x->tx_buf = &ts->read_z2;
x->len = 1;
spi_message_add_tail(x, m);
x->len = 2;
spi_message_add_tail(x, m);
-- m->complete = ads7846_rx_val;
++ m->complete = ads7846_debounce;
m->context = ts;
}
ts->last_msg = m;
- if (request_irq(spi->irq, ads7846_irq,
- IRQF_SAMPLE_RANDOM | IRQF_TRIGGER_FALLING,
- spi->dev.bus_id, ts)) {
+ if (request_irq(spi->irq, ads7846_irq, IRQF_TRIGGER_FALLING,
+ spi->dev.driver->name, ts)) {
dev_dbg(&spi->dev, "irq %d busy?\n", spi->irq);
err = -EBUSY;
-- goto err_cleanup_filter;
++ goto err_free_mem;
}
- dev_info(&spi->dev, "touchscreen + hwmon, irq %d\n", spi->irq);
- err = ads784x_hwmon_register(spi, ts);
- if (err)
- goto err_free_irq;
-
+ dev_info(&spi->dev, "touchscreen, irq %d\n", spi->irq);
-- /* take a first sample, leaving nPENIRQ active and vREF off; avoid
++ /* take a first sample, leaving nPENIRQ active; avoid
* the touchscreen, in case it's not connected.
*/
(void) ads7846_read12_ser(&spi->dev,
READ_12BIT_SER(vaux) | ADS_PD10_ALL_ON);
- /* ads7843/7845 don't have temperature sensors, and
- * use the other ADC lines a bit differently too
- */
- if (ts->model == 7846) {
- err = device_create_file(&spi->dev, &dev_attr_temp0);
- if (err)
- goto err_remove_attr7;
- err = device_create_file(&spi->dev, &dev_attr_temp1);
- if (err)
- goto err_remove_attr6;
- }
- /* in1 == vBAT (7846), or a non-scaled ADC input */
- if (ts->model != 7845) {
- err = device_create_file(&spi->dev, &dev_attr_in1_input);
- if (err)
- goto err_remove_attr5;
- err = sysfs_create_group(&spi->dev.kobj, &ads784x_attr_group);
++ switch (ts->model) {
++ case 7846:
++ ts->attr_group = &ads7846_attr_group;
++ break;
++ case 7845:
++ ts->attr_group = &ads7845_attr_group;
++ break;
++ default:
++ ts->attr_group = &ads7843_attr_group;
++ break;
+ }
- /* in0 == a non-scaled ADC input */
- err = device_create_file(&spi->dev, &dev_attr_in0_input);
- if (err)
- goto err_remove_attr4;
-
- /* non-hwmon device attributes */
- err = device_create_file(&spi->dev, &dev_attr_pen_down);
- if (err)
- goto err_remove_attr3;
- err = device_create_file(&spi->dev, &dev_attr_disable);
++ err = sysfs_create_group(&spi->dev.kobj, ts->attr_group);
if (err)
- goto err_remove_attr2;
- goto err_remove_hwmon;
++ goto err_free_irq;
err = input_register_device(input_dev);
if (err)
return 0;
- err_remove_attr1:
- device_remove_file(&spi->dev, &dev_attr_disable);
- err_remove_attr2:
- device_remove_file(&spi->dev, &dev_attr_pen_down);
- err_remove_attr3:
- device_remove_file(&spi->dev, &dev_attr_in0_input);
- err_remove_attr4:
- if (ts->model != 7845)
- device_remove_file(&spi->dev, &dev_attr_in1_input);
- err_remove_attr5:
- if (ts->model == 7846) {
- device_remove_file(&spi->dev, &dev_attr_temp1);
- err_remove_attr6:
- device_remove_file(&spi->dev, &dev_attr_temp0);
- }
- err_remove_attr7:
+ err_remove_attr_group:
- sysfs_remove_group(&spi->dev.kobj, &ads784x_attr_group);
- err_remove_hwmon:
- ads784x_hwmon_unregister(spi, ts);
++ sysfs_remove_group(&spi->dev.kobj, ts->attr_group);
+ err_free_irq:
free_irq(spi->irq, ts);
-- err_cleanup_filter:
-- if (ts->filter_cleanup)
-- ts->filter_cleanup(ts->filter_data);
err_free_mem:
- if (!IS_ERR(hwmon))
- hwmon_device_unregister(hwmon);
input_free_device(input_dev);
kfree(ts);
return err;
{
struct ads7846 *ts = dev_get_drvdata(&spi->dev);
- hwmon_device_unregister(ts->hwmon);
- ads784x_hwmon_unregister(spi, ts);
input_unregister_device(ts->input);
ads7846_suspend(spi, PMSG_SUSPEND);
- device_remove_file(&spi->dev, &dev_attr_disable);
- device_remove_file(&spi->dev, &dev_attr_pen_down);
- if (ts->model == 7846) {
- device_remove_file(&spi->dev, &dev_attr_temp1);
- device_remove_file(&spi->dev, &dev_attr_temp0);
- }
- if (ts->model != 7845)
- device_remove_file(&spi->dev, &dev_attr_in1_input);
- device_remove_file(&spi->dev, &dev_attr_in0_input);
- sysfs_remove_group(&spi->dev.kobj, &ads784x_attr_group);
++ sysfs_remove_group(&spi->dev.kobj, ts->attr_group);
free_irq(ts->spi->irq, ts);
/* suspend left the IRQ disabled */
enable_irq(ts->spi->irq);
- if (ts->filter_cleanup != NULL)
- if (ts->filter_cleanup)
-- ts->filter_cleanup(ts->filter_data);
--
kfree(ts);
dev_dbg(&spi->dev, "unregistered touchscreen\n");
help
This option enables support for the PCEngines WRAP programmable LEDs.
+config LEDS_OMAP_DEBUG
+ boolean "LED Support for OMAP debug board LEDs"
+ depends on LEDS_CLASS=y && ARCH_OMAP
+ help
+ Enables support for the LEDs on the debug board used with OMAP
+ reference boards like H2/H3/H4 and Perseus2. Up to six of these
+ may be claimed by the original ARM debug LED API.
+
+config LEDS_OMAP
+ tristate "LED Support for OMAP GPIO LEDs"
+ depends on LEDS_CLASS && ARCH_OMAP
+ help
+ This option enables support for the LEDs on OMAP processors.
+
+config LEDS_OMAP_PWM
+ tristate "LED Support for OMAP PWM-controlled LEDs"
+ depends on LEDS_CLASS && ARCH_OMAP && OMAP_DM_TIMER
+ help
+ This options enables support for LEDs connected to GPIO lines
+ controlled by a PWM timer on OMAP CPUs.
+
+ config LEDS_H1940
+ tristate "LED Support for iPAQ H1940 device"
+ depends LEDS_CLASS && ARCH_H1940
+ help
+ This option enables support for the LEDs on the h1940.
+
+ config LEDS_COBALT
+ tristate "LED Support for Cobalt Server front LED"
+ depends on LEDS_CLASS && MIPS_COBALT
+ help
+ This option enables support for the front LED on Cobalt Server
+
comment "LED Triggers"
config LEDS_TRIGGERS
obj-$(CONFIG_LEDS_AMS_DELTA) += leds-ams-delta.o
obj-$(CONFIG_LEDS_NET48XX) += leds-net48xx.o
obj-$(CONFIG_LEDS_WRAP) += leds-wrap.o
+obj-$(CONFIG_LEDS_OMAP) += leds-omap.o
+obj-$(CONFIG_LEDS_OMAP_PWM) += leds-omap-pwm.o
+ obj-$(CONFIG_LEDS_H1940) += leds-h1940.o
+ obj-$(CONFIG_LEDS_COBALT) += leds-cobalt.o
# LED Triggers
obj-$(CONFIG_LEDS_TRIGGER_TIMER) += ledtrig-timer.o
obj-$(CONFIG_MTD_NAND_NANDSIM) += nandsim.o
obj-$(CONFIG_MTD_NAND_CS553X) += cs553x_nand.o
obj-$(CONFIG_MTD_NAND_NDFC) += ndfc.o
+obj-$(CONFIG_MTD_NAND_OMAP) += omap-nand-flash.o
+obj-$(CONFIG_MTD_NAND_OMAP_HW) += omap-hw.o
obj-$(CONFIG_MTD_NAND_AT91) += at91_nand.o
+ obj-$(CONFIG_MTD_NAND_BASLER_EXCITE) += excite_nandflash.o
nand-objs := nand_base.o nand_bbt.o
cafe_nand-objs := cafe.o cafe_ecc.o
comment "SPI Protocol Masters"
depends on SPI_MASTER
+config TSC2102
+ depends on SPI_MASTER
+ tristate "TSC2102 codec support"
+ ---help---
+ Say Y here if you want support for the TSC2102 chip. It
+ will be needed for the touchscreen driver on some boards.
++
+ config SPI_AT25
+ tristate "SPI EEPROMs from most vendors"
+ depends on SPI_MASTER && SYSFS
+ help
+ Enable this driver to get read/write support to most SPI EEPROMs,
+ after you configure the board init code to know about each eeprom
+ on your target board.
+
+ This driver can also be built as a module. If so, the module
+ will be called at25.
+
#
# Add new SPI protocol masters in alphabetical order above this line
#
# ... add above this line ...
# SPI protocol drivers (device/link on bus)
+obj-$(CONFIG_TSC2102) += tsc2102.o
+ obj-$(CONFIG_SPI_AT25) += at25.o
# ... add above this line ...
# SPI slave controller drivers (upstream link)
+++ /dev/null
--/*
-- * omap_uwire.c -- MicroWire interface driver for OMAP
-- *
-- * Copyright 2003 MontaVista Software Inc. <source@mvista.com>
-- *
-- * Ported to 2.6 OMAP uwire interface.
-- * Copyright (C) 2004 Texas Instruments.
-- *
- * Generalization patches by Juha Yrjölä <juha.yrjola@nokia.com>
- * Generalization patches by Juha Yrjola <juha.yrjola@nokia.com>
-- *
-- * Copyright (C) 2005 David Brownell (ported to 2.6 SPI interface)
- * Copyright (C) 2006 Nokia
- *
- * Many updates by Imre Deak <imre.deak@nokia.com>
-- *
-- * This program is free software; you can redistribute it and/or modify it
-- * under the terms of the GNU General Public License as published by the
-- * Free Software Foundation; either version 2 of the License, or (at your
-- * option) any later version.
-- *
-- * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
-- * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
-- * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
-- * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
-- * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
-- * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
-- * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
-- * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-- *
-- * You should have received a copy of the GNU General Public License along
-- * with this program; if not, write to the Free Software Foundation, Inc.,
-- * 675 Mass Ave, Cambridge, MA 02139, USA.
-- */
--#include <linux/kernel.h>
--#include <linux/init.h>
--#include <linux/delay.h>
--#include <linux/platform_device.h>
-#include <linux/workqueue.h>
--#include <linux/interrupt.h>
--#include <linux/err.h>
--#include <linux/clk.h>
--
--#include <linux/spi/spi.h>
--#include <linux/spi/spi_bitbang.h>
--
--#include <asm/system.h>
--#include <asm/irq.h>
--#include <asm/hardware.h>
--#include <asm/io.h>
--#include <asm/mach-types.h>
--
--#include <asm/arch/mux.h>
--#include <asm/arch/omap730.h> /* OMAP730_IO_CONF registers */
--
--
--/* FIXME address is now a platform device resource,
-- * and irqs should show there too...
-- */
--#define UWIRE_BASE_PHYS 0xFFFB3000
--#define UWIRE_BASE ((void *__iomem)IO_ADDRESS(UWIRE_BASE_PHYS))
--
--/* uWire Registers: */
--#define UWIRE_IO_SIZE 0x20
--#define UWIRE_TDR 0x00
--#define UWIRE_RDR 0x00
--#define UWIRE_CSR 0x01
--#define UWIRE_SR1 0x02
--#define UWIRE_SR2 0x03
--#define UWIRE_SR3 0x04
--#define UWIRE_SR4 0x05
--#define UWIRE_SR5 0x06
--
--/* CSR bits */
--#define RDRB (1 << 15)
--#define CSRB (1 << 14)
--#define START (1 << 13)
--#define CS_CMD (1 << 12)
--
--/* SR1 or SR2 bits */
--#define UWIRE_READ_FALLING_EDGE 0x0001
--#define UWIRE_READ_RISING_EDGE 0x0000
--#define UWIRE_WRITE_FALLING_EDGE 0x0000
--#define UWIRE_WRITE_RISING_EDGE 0x0002
--#define UWIRE_CS_ACTIVE_LOW 0x0000
--#define UWIRE_CS_ACTIVE_HIGH 0x0004
--#define UWIRE_FREQ_DIV_2 0x0000
--#define UWIRE_FREQ_DIV_4 0x0008
--#define UWIRE_FREQ_DIV_8 0x0010
--#define UWIRE_CHK_READY 0x0020
--#define UWIRE_CLK_INVERTED 0x0040
--
--
--struct uwire_spi {
-- struct spi_bitbang bitbang;
-- struct clk *ck;
--};
--
--struct uwire_state {
-- unsigned bits_per_word;
-- unsigned div1_idx;
--};
--
--/* REVISIT compile time constant for idx_shift? */
--static unsigned int uwire_idx_shift;
--
--static inline void uwire_write_reg(int idx, u16 val)
--{
-- __raw_writew(val, UWIRE_BASE + (idx << uwire_idx_shift));
--}
--
--static inline u16 uwire_read_reg(int idx)
--{
-- return __raw_readw(UWIRE_BASE + (idx << uwire_idx_shift));
--}
--
--static inline void omap_uwire_configure_mode(u8 cs, unsigned long flags)
--{
-- u16 w, val = 0;
-- int shift, reg;
--
-- if (flags & UWIRE_CLK_INVERTED)
-- val ^= 0x03;
-- val = flags & 0x3f;
-- if (cs & 1)
-- shift = 6;
-- else
-- shift = 0;
-- if (cs <= 1)
-- reg = UWIRE_SR1;
-- else
-- reg = UWIRE_SR2;
--
-- w = uwire_read_reg(reg);
-- w &= ~(0x3f << shift);
-- w |= val << shift;
-- uwire_write_reg(reg, w);
--}
--
--static int wait_uwire_csr_flag(u16 mask, u16 val, int might_not_catch)
--{
-- u16 w;
-- int c = 0;
-- unsigned long max_jiffies = jiffies + HZ;
--
-- for (;;) {
-- w = uwire_read_reg(UWIRE_CSR);
-- if ((w & mask) == val)
-- break;
-- if (time_after(jiffies, max_jiffies)) {
-- printk(KERN_ERR "%s: timeout. reg=%#06x "
-- "mask=%#06x val=%#06x\n",
-- __FUNCTION__, w, mask, val);
-- return -1;
-- }
-- c++;
-- if (might_not_catch && c > 64)
-- break;
-- }
-- return 0;
--}
--
--static void uwire_set_clk1_div(int div1_idx)
--{
-- u16 w;
--
-- w = uwire_read_reg(UWIRE_SR3);
-- w &= ~(0x03 << 1);
-- w |= div1_idx << 1;
-- uwire_write_reg(UWIRE_SR3, w);
--}
--
--static void uwire_chipselect(struct spi_device *spi, int value)
--{
-- struct uwire_state *ust = spi->controller_state;
-- u16 w;
-- int old_cs;
--
--
-- BUG_ON(wait_uwire_csr_flag(CSRB, 0, 0));
--
-- w = uwire_read_reg(UWIRE_CSR);
-- old_cs = (w >> 10) & 0x03;
-- if (value == BITBANG_CS_INACTIVE || old_cs != spi->chip_select) {
-- /* Deselect this CS, or the previous CS */
-- w &= ~CS_CMD;
-- uwire_write_reg(UWIRE_CSR, w);
-- }
-- /* activate specfied chipselect */
-- if (value == BITBANG_CS_ACTIVE) {
-- uwire_set_clk1_div(ust->div1_idx);
-- /* invert clock? */
-- if (spi->mode & SPI_CPOL)
-- uwire_write_reg(UWIRE_SR4, 1);
-- else
-- uwire_write_reg(UWIRE_SR4, 0);
--
-- w = spi->chip_select << 10;
-- w |= CS_CMD;
-- uwire_write_reg(UWIRE_CSR, w);
-- }
--}
--
--static int uwire_txrx(struct spi_device *spi, struct spi_transfer *t)
--{
-- struct uwire_state *ust = spi->controller_state;
-- unsigned len = t->len;
-- unsigned bits = ust->bits_per_word;
-- unsigned bytes;
-- u16 val, w;
-- int status = 0;;
--
-- if (!t->tx_buf && !t->rx_buf)
-- return 0;
--
-- /* Microwire doesn't read and write concurrently */
-- if (t->tx_buf && t->rx_buf)
-- return -EPERM;
--
-- w = spi->chip_select << 10;
-- w |= CS_CMD;
--
-- if (t->tx_buf) {
-- const u8 *buf = t->tx_buf;
--
-- /* NOTE: DMA could be used for TX transfers */
--
-- /* write one or two bytes at a time */
-- while (len >= 1) {
-- /* tx bit 15 is first sent; we byteswap multibyte words
-- * (msb-first) on the way out from memory.
-- */
-- val = *buf++;
-- if (bits > 8) {
-- bytes = 2;
-- val |= *buf++ << 8;
-- } else
-- bytes = 1;
-- val <<= 16 - bits;
--
--#ifdef VERBOSE
-- pr_debug("%s: write-%d =%04x\n",
-- spi->dev.bus_id, bits, val);
--#endif
-- if (wait_uwire_csr_flag(CSRB, 0, 0))
-- goto eio;
--
-- uwire_write_reg(UWIRE_TDR, val);
--
-- /* start write */
-- val = START | w | (bits << 5);
--
-- uwire_write_reg(UWIRE_CSR, val);
-- len -= bytes;
--
-- /* Wait till write actually starts.
-- * This is needed with MPU clock 60+ MHz.
-- * REVISIT: we may not have time to catch it...
-- */
-- if (wait_uwire_csr_flag(CSRB, CSRB, 1))
-- goto eio;
--
-- status += bytes;
-- }
--
-- /* REVISIT: save this for later to get more i/o overlap */
-- if (wait_uwire_csr_flag(CSRB, 0, 0))
-- goto eio;
--
-- } else if (t->rx_buf) {
-- u8 *buf = t->rx_buf;
--
-- /* read one or two bytes at a time */
-- while (len) {
-- if (bits > 8) {
-- bytes = 2;
-- } else
-- bytes = 1;
--
-- /* start read */
-- val = START | w | (bits << 0);
-- uwire_write_reg(UWIRE_CSR, val);
-- len -= bytes;
--
-- /* Wait till read actually starts */
-- (void) wait_uwire_csr_flag(CSRB, CSRB, 1);
--
-- if (wait_uwire_csr_flag(RDRB | CSRB,
-- RDRB, 0))
-- goto eio;
--
-- /* rx bit 0 is last received; multibyte words will
-- * be properly byteswapped on the way to memory.
-- */
-- val = uwire_read_reg(UWIRE_RDR);
-- val &= (1 << bits) - 1;
-- *buf++ = (u8) val;
-- if (bytes == 2)
-- *buf++ = val >> 8;
-- status += bytes;
--#ifdef VERBOSE
-- pr_debug("%s: read-%d =%04x\n",
-- spi->dev.bus_id, bits, val);
--#endif
--
-- }
-- }
-- return status;
--eio:
-- return -EIO;
--}
--
--static int uwire_setup_transfer(struct spi_device *spi, struct spi_transfer *t)
--{
-- struct uwire_state *ust = spi->controller_state;
-- struct uwire_spi *uwire;
-- unsigned flags = 0;
-- unsigned bits;
-- unsigned hz;
-- unsigned long rate;
-- int div1_idx;
-- int div1;
-- int div2;
-- int status;
--
-- uwire = spi_master_get_devdata(spi->master);
--
-- if (spi->chip_select > 3) {
-- pr_debug("%s: cs%d?\n", spi->dev.bus_id, spi->chip_select);
-- status = -ENODEV;
-- goto done;
-- }
--
-- bits = spi->bits_per_word;
-- if (t != NULL && t->bits_per_word)
-- bits = t->bits_per_word;
-- if (!bits)
-- bits = 8;
--
-- if (bits > 16) {
-- pr_debug("%s: wordsize %d?\n", spi->dev.bus_id, bits);
-- status = -ENODEV;
-- goto done;
-- }
-- ust->bits_per_word = bits;
--
-- /* mode 0..3, clock inverted separately;
-- * standard nCS signaling;
-- * don't treat DI=high as "not ready"
-- */
-- if (spi->mode & SPI_CS_HIGH)
-- flags |= UWIRE_CS_ACTIVE_HIGH;
--
-- if (spi->mode & SPI_CPOL)
-- flags |= UWIRE_CLK_INVERTED;
--
-- switch (spi->mode & (SPI_CPOL | SPI_CPHA)) {
-- case SPI_MODE_0:
-- case SPI_MODE_3:
-- flags |= UWIRE_WRITE_RISING_EDGE | UWIRE_READ_FALLING_EDGE;
-- break;
-- case SPI_MODE_1:
-- case SPI_MODE_2:
-- flags |= UWIRE_WRITE_FALLING_EDGE | UWIRE_READ_RISING_EDGE;
-- break;
-- }
--
-- /* assume it's already enabled */
-- rate = clk_get_rate(uwire->ck);
--
-- hz = spi->max_speed_hz;
-- if (t != NULL && t->speed_hz)
-- hz = t->speed_hz;
--
-- if (!hz) {
-- pr_debug("%s: zero speed?\n", spi->dev.bus_id);
-- status = -EINVAL;
-- goto done;
-- }
--
-- /* F_INT = mpu_xor_clk / DIV1 */
-- for (div1_idx = 0; div1_idx < 4; div1_idx++) {
-- switch (div1_idx) {
-- case 0:
-- div1 = 2;
-- break;
-- case 1:
-- div1 = 4;
-- break;
-- case 2:
-- div1 = 7;
-- break;
-- default:
-- case 3:
-- div1 = 10;
-- break;
-- }
-- div2 = (rate / div1 + hz - 1) / hz;
-- if (div2 <= 8)
-- break;
-- }
-- if (div1_idx == 4) {
-- pr_debug("%s: lowest clock %ld, need %d\n",
-- spi->dev.bus_id, rate / 10 / 8, hz);
- status = -EDOM;
- goto done;
- status = -EDOM;
- goto done;
-- }
--
-- /* we have to cache this and reset in uwire_chipselect as this is a
-- * global parameter and another uwire device can change it under
-- * us */
-- ust->div1_idx = div1_idx;
-- uwire_set_clk1_div(div1_idx);
--
-- rate /= div1;
--
-- switch (div2) {
-- case 0:
-- case 1:
-- case 2:
-- flags |= UWIRE_FREQ_DIV_2;
-- rate /= 2;
-- break;
-- case 3:
-- case 4:
-- flags |= UWIRE_FREQ_DIV_4;
-- rate /= 4;
-- break;
-- case 5:
-- case 6:
-- case 7:
-- case 8:
-- flags |= UWIRE_FREQ_DIV_8;
-- rate /= 8;
-- break;
-- }
-- omap_uwire_configure_mode(spi->chip_select, flags);
-- pr_debug("%s: uwire flags %02x, armxor %lu KHz, SCK %lu KHz\n",
-- __FUNCTION__, flags,
-- clk_get_rate(uwire->ck) / 1000,
-- rate / 1000);
-- status = 0;
--done:
-- return status;
--}
--
--static int uwire_setup(struct spi_device *spi)
--{
-- struct uwire_state *ust = spi->controller_state;
--
-- if (ust == NULL) {
-- ust = kzalloc(sizeof(*ust), GFP_KERNEL);
-- if (ust == NULL)
-- return -ENOMEM;
-- spi->controller_state = ust;
-- }
--
-- return uwire_setup_transfer(spi, NULL);
--}
--
- static void uwire_cleanup(const struct spi_device *spi)
-static void uwire_cleanup(struct spi_device *spi)
--{
-- kfree(spi->controller_state);
--}
--
--static void uwire_off(struct uwire_spi *uwire)
--{
-- uwire_write_reg(UWIRE_SR3, 0);
-- clk_disable(uwire->ck);
-- clk_put(uwire->ck);
-- spi_master_put(uwire->bitbang.master);
--}
--
--static int uwire_probe(struct platform_device *pdev)
--{
-- struct spi_master *master;
-- struct uwire_spi *uwire;
-- int status;
--
-- master = spi_alloc_master(&pdev->dev, sizeof *uwire);
-- if (!master)
-- return -ENODEV;
--
-- uwire = spi_master_get_devdata(master);
-- dev_set_drvdata(&pdev->dev, uwire);
--
-- uwire->ck = clk_get(&pdev->dev, "armxor_ck");
-- if (!uwire->ck || IS_ERR(uwire->ck)) {
-- dev_dbg(&pdev->dev, "no mpu_xor_clk ?\n");
-- spi_master_put(master);
-- return -ENODEV;
-- }
-- clk_enable(uwire->ck);
--
-- if (cpu_is_omap730())
-- uwire_idx_shift = 1;
-- else
-- uwire_idx_shift = 2;
--
-- uwire_write_reg(UWIRE_SR3, 1);
--
-- master->bus_num = 2; /* "official" */
-- master->num_chipselect = 4;
-- master->setup = uwire_setup;
-- master->cleanup = uwire_cleanup;
--
-- uwire->bitbang.master = master;
-- uwire->bitbang.chipselect = uwire_chipselect;
-- uwire->bitbang.setup_transfer = uwire_setup_transfer;
-- uwire->bitbang.txrx_bufs = uwire_txrx;
--
-- status = spi_bitbang_start(&uwire->bitbang);
-- if (status < 0)
-- uwire_off(uwire);
-- return status;
--}
--
--static int uwire_remove(struct platform_device *pdev)
--{
-- struct uwire_spi *uwire = dev_get_drvdata(&pdev->dev);
-- int status;
--
-- // FIXME remove all child devices, somewhere ...
--
-- status = spi_bitbang_stop(&uwire->bitbang);
-- uwire_off(uwire);
-- return status;
--}
--
--static struct platform_driver uwire_driver = {
-- .driver = {
-- .name = "omap_uwire",
-- .bus = &platform_bus_type,
-- .owner = THIS_MODULE,
-- },
-- .probe = uwire_probe,
-- .remove = uwire_remove,
-- // suspend ... unuse ck
-- // resume ... use ck
--};
--
--static int __init omap_uwire_init(void)
--{
-- /* FIXME move these into the relevant board init code. also, include
-- * H3 support; it uses tsc2101 like H2 (on a different chipselect).
-- */
--
-- if (machine_is_omap_h2()) {
-- /* defaults: W21 SDO, U18 SDI, V19 SCL */
-- omap_cfg_reg(N14_1610_UWIRE_CS0);
-- omap_cfg_reg(N15_1610_UWIRE_CS1);
-- }
-- if (machine_is_omap_perseus2()) {
-- /* configure pins: MPU_UW_nSCS1, MPU_UW_SDO, MPU_UW_SCLK */
-- int val = omap_readl(OMAP730_IO_CONF_9) & ~0x00EEE000;
-- omap_writel(val | 0x00AAA000, OMAP730_IO_CONF_9);
-- }
--
-- return platform_driver_register(&uwire_driver);
--}
--
--static void __exit omap_uwire_exit(void)
--{
-- platform_driver_unregister(&uwire_driver);
--}
--
--subsys_initcall(omap_uwire_init);
--module_exit(omap_uwire_exit);
--
--MODULE_LICENSE("GPL");
-
source "drivers/video/logo/Kconfig"
endif
- if SYSFS
- source "drivers/video/backlight/Kconfig"
-if ARCH_OMAP
- source "drivers/video/omap/Kconfig"
--endif
--
endmenu
If you have a HP Jornada 680, say y to enable the
backlight driver.
+config BACKLIGHT_OMAP
+ tristate "OMAP LCD Backlight"
+ depends on BACKLIGHT_DEVICE && (ARCH_OMAP1 || ARCH_OMAP2)
+ default y
+ help
+ This driver controls the LCD backlight level and power
+ for the PWL module of OMAP processors. Say Y if you plan
+ to use power saving.
++
+ config BACKLIGHT_PROGEAR
+ tristate "Frontpath ProGear Backlight Driver"
+ depends on BACKLIGHT_CLASS_DEVICE && PCI && X86
+ default n
+ help
+ If you have a Frontpath ProGear say Y to enable the
+ backlight driver.
obj-$(CONFIG_BACKLIGHT_CORGI) += corgi_bl.o
obj-$(CONFIG_BACKLIGHT_HP680) += hp680_bl.o
obj-$(CONFIG_BACKLIGHT_LOCOMO) += locomolcd.o
+obj-$(CONFIG_BACKLIGHT_OMAP) += omap_bl.o
+ obj-$(CONFIG_BACKLIGHT_PROGEAR) += progear_bl.o
#define I2C_DRIVERID_KS0127 86 /* Samsung ks0127 video decoder */
#define I2C_DRIVERID_TLV320AIC23B 87 /* TI TLV320AIC23B audio codec */
#define I2C_DRIVERID_ISL1208 88 /* Intersil ISL1208 RTC */
+ #define I2C_DRIVERID_WM8731 89 /* Wolfson WM8731 audio codec */
+ #define I2C_DRIVERID_WM8750 90 /* Wolfson WM8750 audio codec */
+
+ #define I2C_DRIVERID_MISC 99 /* Whatever until sorted out */
+#define I2C_DRIVERID_MISC 99 /* Whatever until sorted out */
+
#define I2C_DRIVERID_I2CDEV 900
#define I2C_DRIVERID_ARP 902 /* SMBus ARP Client */
#define I2C_DRIVERID_ALERT 903 /* SMBus Alert Responder Client */
*
* It's OK if the min/max values are zero.
*/
--enum ads7846_filter {
-- ADS7846_FILTER_OK,
-- ADS7846_FILTER_REPEAT,
-- ADS7846_FILTER_IGNORE,
--};
--
struct ads7846_platform_data {
u16 model; /* 7843, 7845, 7846. */
u16 vref_delay_usecs; /* 0 for external vref; etc */
- int keep_vref_on : 1; /* set to keep vref on for differential
- int keep_vref_on:1; /* set to keep vref on for differential
-- * measurements as well */
u16 x_plate_ohms;
u16 y_plate_ohms;
u16 debounce_rep; /* additional consecutive good readings
* required after the first two */
int (*get_pendown_state)(void);
-- int (*filter_init) (struct ads7846_platform_data *pdata,
-- void **filter_data);
-- int (*filter) (void *filter_data, int data_idx, int *val);
-- void (*filter_cleanup)(void *filter_data);
};