mirror of
https://github.com/hardkernel/linux.git
synced 2026-06-08 20:07:46 +09:00
1,耳机按键;2,针对raho的震动(time 精度还不行);3,modem控制驱动;4,一些log开关的修改
This commit is contained in:
@@ -1846,6 +1846,13 @@ struct platform_device rk2818_device_dm9k = {
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_STE
|
||||
struct platform_device rk2818_device_ste = {
|
||||
.name = "ste",
|
||||
.id = -1,
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_HEADSET_DET
|
||||
struct rk2818_headset_data rk2818_headset_info = {
|
||||
.irq = FPGA_PIO0_00,
|
||||
@@ -1862,6 +1869,81 @@ struct platform_device rk28_device_headset = {
|
||||
};
|
||||
#endif
|
||||
|
||||
// adc ---> key
|
||||
#define PLAY_ON_PIN RK2818_PIN_PA3
|
||||
#define PLAY_ON_LEVEL 1
|
||||
static ADC_keyst gAdcValueTab[] =
|
||||
{
|
||||
{0x65, AD2KEY2},///VOLUME_DOWN
|
||||
{0xd3, AD2KEY1},///VOLUME_UP
|
||||
{0x130, AD2KEY3},///MENU
|
||||
{0x19d, AD2KEY4},///HOME
|
||||
{0x202, AD2KEY5},///BACK
|
||||
{0x2d0, AD2KEY6},///CALL
|
||||
{0x267, AD2KEY7},///SEARCH
|
||||
{0, 0}///table end
|
||||
};
|
||||
|
||||
static unsigned char gInitKeyCode[] =
|
||||
{
|
||||
AD2KEY1,AD2KEY2,AD2KEY3,AD2KEY4,AD2KEY5,AD2KEY6,AD2KEY7,
|
||||
ENDCALL,KEYSTART,KEY_WAKEUP,
|
||||
};
|
||||
|
||||
struct adc_key_data rk2818_adc_key = {
|
||||
.pin_playon = PLAY_ON_PIN,
|
||||
.playon_level = PLAY_ON_LEVEL,
|
||||
.adc_empty = 1000,
|
||||
.adc_invalid = 20,
|
||||
.adc_drift = 50,
|
||||
.adc_chn = 1,
|
||||
.adc_key_table = gAdcValueTab,
|
||||
.initKeyCode = gInitKeyCode,
|
||||
.adc_key_cnt = 10,
|
||||
};
|
||||
|
||||
struct rk2818_adckey_platform_data rk2818_adckey_platdata = {
|
||||
.adc_key = &rk2818_adc_key,
|
||||
};
|
||||
|
||||
//headset key
|
||||
#ifdef CONFIG_HEADSET_KEY
|
||||
static ADC_keyst gHskeyValueTab[] =
|
||||
{
|
||||
{0, KEY_HEADSETHOOK},
|
||||
{0, 0}///table end
|
||||
};
|
||||
|
||||
static unsigned char gInitHsKeyCode[] =
|
||||
{
|
||||
KEY_HEADSETHOOK,
|
||||
};
|
||||
|
||||
struct adc_key_data rk2818_hs_key = {
|
||||
.pin_playon = 0,
|
||||
.playon_level = 0,
|
||||
.adc_empty = 0,
|
||||
.adc_invalid = 0,
|
||||
.adc_drift = 50,
|
||||
.adc_chn = 2,
|
||||
.adc_key_table = gHskeyValueTab,
|
||||
.initKeyCode = gInitHsKeyCode,
|
||||
.adc_key_cnt = 1,
|
||||
};
|
||||
|
||||
struct rk2818_adckey_platform_data rk2818_hskey_platdata = {
|
||||
.adc_key = &rk2818_hs_key,
|
||||
};
|
||||
|
||||
struct platform_device rk2818_device_hskey = {
|
||||
.name = "rk2818-hskey",
|
||||
.id = -1,
|
||||
.dev = {
|
||||
.platform_data = &rk2818_hskey_platdata,
|
||||
}
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_INPUT_LPSENSOR_CM3602
|
||||
static int capella_cm3602_power(int on);
|
||||
|
||||
@@ -2012,6 +2094,9 @@ static struct platform_device *devices[] __initdata = {
|
||||
#ifdef CONFIG_HEADSET_DET
|
||||
&rk28_device_headset,
|
||||
#endif
|
||||
#ifdef CONFIG_HEADSET_KEY
|
||||
&rk2818_device_hskey,
|
||||
#endif
|
||||
#ifdef CONFIG_DWC_OTG
|
||||
&rk2818_device_dwc_otg,
|
||||
#endif
|
||||
@@ -2022,6 +2107,9 @@ static struct platform_device *devices[] __initdata = {
|
||||
&android_usb_device,
|
||||
&usb_mass_storage_device,
|
||||
#endif
|
||||
#ifdef CONFIG_STE
|
||||
&rk2818_device_ste,
|
||||
#endif
|
||||
#ifdef CONFIG_ANDROID_TIMED_GPIO
|
||||
&rk28_device_vibrator,
|
||||
#endif
|
||||
@@ -2057,50 +2145,13 @@ static void rk2818_power_off(void)
|
||||
gpio_set_value(POWER_PIN, 0);/*power down*/
|
||||
}
|
||||
|
||||
// adc ---> key
|
||||
#define PLAY_ON_PIN RK2818_PIN_PA3
|
||||
#define PLAY_ON_LEVEL 1
|
||||
static ADC_keyst gAdcValueTab[] =
|
||||
{
|
||||
{0x65, AD2KEY1},///VOLUME_DOWN
|
||||
{0xd3, AD2KEY2},///VOLUME_UP
|
||||
{0x130, AD2KEY3},///MENU
|
||||
{0x19d, AD2KEY4},///HOME
|
||||
{0x202, AD2KEY5},///BACK
|
||||
{0x2d0, AD2KEY6},///CALL
|
||||
{0x267, AD2KEY7},///SEARCH
|
||||
{0, 0}///table end
|
||||
};
|
||||
|
||||
static unsigned char gInitKeyCode[] =
|
||||
{
|
||||
AD2KEY1,AD2KEY2,AD2KEY3,AD2KEY4,AD2KEY5,AD2KEY6,AD2KEY7,
|
||||
ENDCALL,KEYSTART,KEY_WAKEUP,
|
||||
};
|
||||
|
||||
struct adc_key_data rk2818_adc_key = {
|
||||
.pin_playon = PLAY_ON_PIN,
|
||||
.playon_level = PLAY_ON_LEVEL,
|
||||
.adc_empty = 1000,
|
||||
.adc_invalid = 20,
|
||||
.adc_drift = 50,
|
||||
.adc_chn = 1,
|
||||
.adc_key_table = gAdcValueTab,
|
||||
.initKeyCode = gInitKeyCode,
|
||||
.adc_key_cnt = 10,
|
||||
};
|
||||
|
||||
struct rk2818_adckey_platform_data rk2818_adckey_platdata = {
|
||||
.adc_key = &rk2818_adc_key,
|
||||
};
|
||||
|
||||
#if CONFIG_ANDROID_TIMED_GPIO
|
||||
#if defined(CONFIG_ANDROID_TIMED_GPIO)
|
||||
static struct timed_gpio timed_gpios[] = {
|
||||
{
|
||||
.name = "vibrator",
|
||||
.gpio = FPGA_PIO1_12,
|
||||
.max_timeout = 1000,
|
||||
.active_low = 1,
|
||||
.active_low = 0,
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
@@ -237,6 +237,7 @@ struct rk2818_rtc_platform_data {
|
||||
#define KEYMENU AD2KEY6 ///CALL
|
||||
#define KEY_PLAY_SHORT_PRESS KEYSTART //code for short press the play key
|
||||
#define KEY_PLAY_LONG_PRESS ENDCALL //code for long press the play key
|
||||
#define KEY_HEADSETHOOK 226
|
||||
|
||||
//ADC Registers
|
||||
typedef struct tagADC_keyst
|
||||
|
||||
@@ -69,7 +69,11 @@ MUX_CFG(GPIOB3_U0RTSN_SEL_NAME, B, 13, 1, 0, DEFAULT) /* 0 : gpio_b3 1
|
||||
MUX_CFG(GPIOB2_U0CTSN_SEL_NAME, B, 12, 1, 0, DEFAULT) /* 0 : gpio_b2 1 : uart0_cts_n */
|
||||
MUX_CFG(GPIOF2_APWM0_SEL_NAME, B, 11, 1, 0, INITIAL) /* 0 : gpio_f2 1 : pwm0 */
|
||||
MUX_CFG(GPIOC_LCDC16BIT_SEL_NAME, B, 10, 1, 1, INITIAL) /* 0 : gpio_d0 ~ gpio_d7 1 : lcdc_data8 ~ lcdc_data15 */
|
||||
#if defined(CONFIG_MACH_RAHO)||defined(CONFIG_MACH_RAHO_0928)
|
||||
MUX_CFG(GPIOC_LCDC24BIT_SEL_NAME, B, 9, 1, 0, INITIAL) /* 0 : gpio_c2 ~ gpio_c7 1 : lcdc_data18 ~ lcdc_data23 */
|
||||
#else
|
||||
MUX_CFG(GPIOC_LCDC24BIT_SEL_NAME, B, 9, 1, 1, INITIAL) /* 0 : gpio_c2 ~ gpio_c7 1 : lcdc_data18 ~ lcdc_data23 */
|
||||
#endif
|
||||
MUX_CFG(GPIOC_LCDC18BIT_SEL_NAME, B, 8, 1, 1, INITIAL) /* 0 : gpio_c0/c1 1 : lcdc_data16 ~ lcdc_data17 */
|
||||
MUX_CFG(CXGPIO_LCDDEN_SEL_NAME, B, 7, 1, 1, INITIAL) /* 0 : gpio2_26 1 : lcdc_denable */
|
||||
MUX_CFG(CXGPIO_LCDVSYNC_SEL_NAME, B, 6, 1, 1, INITIAL) /* 0 : gpio2_25 1 : lcdc_vsync */
|
||||
|
||||
@@ -61,6 +61,16 @@ static struct rk2818_headset_data *prk2818_headset_info;
|
||||
static irqreturn_t headset_interrupt(int irq, void *dev_id);
|
||||
unsigned int headset_irq_type;
|
||||
|
||||
int headset_status(void)
|
||||
{
|
||||
if(Headset_dev.cur_headset_status & BIT_HEADSET)
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
EXPORT_SYMBOL_GPL(headset_status);
|
||||
|
||||
static void headsetobserve_work(void)
|
||||
{
|
||||
if(gpio_get_value(prk2818_headset_info->irq)){
|
||||
|
||||
@@ -432,6 +432,17 @@ config KEYBOARD_RK28ADC
|
||||
|
||||
To compile this driver as a module, choose M here: the
|
||||
module will be called rk2818_adckey.
|
||||
|
||||
config HEADSET_KEY
|
||||
tristate "RK2818 headset Keypad support"
|
||||
depends on RK28_ADC
|
||||
default y
|
||||
help
|
||||
Say Y here to enable the headset adc keypad on SDK board
|
||||
based on RK2818.
|
||||
|
||||
To compile this driver as a module, choose M here: the
|
||||
module will be called rk2818_hskey.
|
||||
|
||||
config KEYBOARD_RK28ADC_IT50
|
||||
tristate "RK2818 ADC Keypad it50 support"
|
||||
|
||||
@@ -39,4 +39,5 @@ obj-$(CONFIG_KEYBOARD_XTKBD) += xtkbd.o
|
||||
obj-$(CONFIG_KEYBOARD_W90P910) += w90p910_keypad.o
|
||||
obj-$(CONFIG_KEYBOARD_RK28ADC) += rk2818_adckey.o
|
||||
obj-$(CONFIG_KEYBOARD_RK28ADC_IT50) += rk2818_adckey_t50.o
|
||||
obj-$(CONFIG_HEADSET_KEY) += rk2818_hskey.o
|
||||
|
||||
|
||||
@@ -59,8 +59,10 @@ struct rk28_adckey *pRk28AdcKey;
|
||||
|
||||
unsigned int rk28_get_keycode(unsigned int advalue,pADC_keyst ptab,struct adc_key_data *rk2818_adckey_data)
|
||||
{
|
||||
while(ptab->adc_value != 0)
|
||||
while(ptab->adc_keycode != 0)
|
||||
{
|
||||
if((ptab->adc_value == 0)&&(advalue >= 0 && advalue <= 5))
|
||||
return ptab->adc_keycode;
|
||||
if((advalue > ptab->adc_value - rk2818_adckey_data->adc_drift) && (advalue < ptab->adc_value + rk2818_adckey_data->adc_drift))
|
||||
return ptab->adc_keycode;
|
||||
ptab++;
|
||||
@@ -69,6 +71,8 @@ unsigned int rk28_get_keycode(unsigned int advalue,pADC_keyst ptab,struct adc_ke
|
||||
return 0;
|
||||
}
|
||||
|
||||
EXPORT_SYMBOL_GPL(rk28_get_keycode);
|
||||
|
||||
static irqreturn_t rk28_playkey_irq(int irq, void *handle)
|
||||
{
|
||||
|
||||
|
||||
284
drivers/input/keyboard/rk2818_hskey.c
Normal file
284
drivers/input/keyboard/rk2818_hskey.c
Normal file
@@ -0,0 +1,284 @@
|
||||
/*
|
||||
* linux/drivers/input/keyboard/rk28_adckey.c
|
||||
*
|
||||
* This driver program support to AD key which use for rk28 chip
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/interrupt.h>
|
||||
#include <linux/input.h>
|
||||
#include <linux/device.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/clk.h>
|
||||
#include <linux/err.h>
|
||||
#include <linux/delay.h>
|
||||
|
||||
#include <asm/mach-types.h>
|
||||
#include <asm/mach/arch.h>
|
||||
#include <asm/mach/map.h>
|
||||
#include <mach/gpio.h>
|
||||
#include <mach/adc.h>
|
||||
#include <mach/board.h>
|
||||
|
||||
#if 1
|
||||
#define DBG(x...) printk(x)
|
||||
#else
|
||||
#define DBG(x...)
|
||||
#endif
|
||||
|
||||
//#define KEY_PHYS_NAME "rk2818_adckey/input0"
|
||||
|
||||
static unsigned int gLastKeyCode = 0;
|
||||
static int gSampleTimes = 0;
|
||||
static int gADValue = 0;
|
||||
static struct rk28_hskey *phsKey;
|
||||
|
||||
//key code tab
|
||||
struct rk28_hskey
|
||||
{
|
||||
struct input_dev *input_dev;
|
||||
struct timer_list timer;
|
||||
unsigned char * keycodes;
|
||||
};
|
||||
|
||||
extern int headset_status(void);
|
||||
extern unsigned int rk28_get_keycode(unsigned int advalue,pADC_keyst ptab,struct adc_key_data *rk2818_adckey_data);
|
||||
|
||||
#if 0
|
||||
unsigned int rk28_get_keycode(unsigned int advalue,pADC_keyst ptab,struct adc_key_data *rk2818_adckey_data)
|
||||
{
|
||||
while(ptab->adc_keycode != 0)
|
||||
{
|
||||
if((ptab->adc_value == 0)&&(advalue >= 0 && advalue <= 5))
|
||||
return ptab->adc_keycode;
|
||||
if((advalue > ptab->adc_value - rk2818_adckey_data->adc_drift) && (advalue < ptab->adc_value + rk2818_adckey_data->adc_drift))
|
||||
return ptab->adc_keycode;
|
||||
ptab++;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void rk28_send_wakeup_key( void )
|
||||
{
|
||||
input_report_key(phsKey->input_dev,KEY_WAKEUP,1);
|
||||
input_sync(phsKey->input_dev);
|
||||
input_report_key(phsKey->input_dev,KEY_WAKEUP,0);
|
||||
input_sync(phsKey->input_dev);
|
||||
DBG("Wake up system\n");
|
||||
}
|
||||
#endif
|
||||
|
||||
static int rk28_Hskey_open(struct input_dev *dev)
|
||||
{
|
||||
//struct rk28_adckey *adckey = input_get_drvdata(dev);
|
||||
DBG("===========rk28_Hskey_open===========\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void rk28_Hskey_close(struct input_dev *dev)
|
||||
{
|
||||
DBG("===========rk28_Hskey_close===========\n");
|
||||
//struct rk28_adckey *adckey = input_get_drvdata(dev);
|
||||
//
|
||||
}
|
||||
|
||||
#ifdef CONFIG_PM
|
||||
static int rk28_hskey_suspend(struct platform_device *pdev, pm_message_t state)
|
||||
{
|
||||
//struct rk28_adckey *adckey = platform_get_drvdata(pdev);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rk28_hskey_resume(struct platform_device *pdev)
|
||||
{
|
||||
//struct rk28_adckey *adckey = platform_get_drvdata(pdev);
|
||||
//struct input_dev *input_dev = adckey->input_dev;
|
||||
#if 0
|
||||
mutex_lock(&input_dev->mutex);
|
||||
|
||||
mutex_unlock(&input_dev->mutex);
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
#else
|
||||
#define rk28_hskey_suspend NULL
|
||||
#define rk28_hskey_resume NULL
|
||||
#endif
|
||||
static void rk28_hskeyscan_timer(unsigned long data)
|
||||
{
|
||||
unsigned int adcvalue = 0x3FF,code = 0;
|
||||
struct adc_key_data *rk2818_adckey_data = (struct adc_key_data *)data;
|
||||
|
||||
phsKey->timer.expires = jiffies + msecs_to_jiffies(10);
|
||||
add_timer(&phsKey->timer);
|
||||
|
||||
if(headset_status())
|
||||
{
|
||||
if(gSampleTimes<4)
|
||||
{
|
||||
gADValue += gAdcValue[rk2818_adckey_data->adc_chn];
|
||||
gSampleTimes++;
|
||||
}
|
||||
else
|
||||
{
|
||||
gADValue = gADValue/4;
|
||||
code=rk28_get_keycode(gADValue,rk2818_adckey_data->adc_key_table,rk2818_adckey_data);
|
||||
gADValue = 0;
|
||||
gSampleTimes = 0;
|
||||
|
||||
if(code && !gLastKeyCode)
|
||||
{
|
||||
gLastKeyCode = code;
|
||||
input_report_key(phsKey->input_dev,gLastKeyCode,1);
|
||||
input_sync(phsKey->input_dev);
|
||||
DBG("===========headset key press code=%d ===========\n",code);
|
||||
}
|
||||
else if(!code && gLastKeyCode)
|
||||
{
|
||||
input_report_key(phsKey->input_dev,gLastKeyCode,0);
|
||||
input_sync(phsKey->input_dev);
|
||||
gLastKeyCode = 0;
|
||||
DBG("===========headset key release code=%d ===========\n",code);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if(gLastKeyCode)
|
||||
{
|
||||
input_report_key(phsKey->input_dev,code,0);
|
||||
input_sync(phsKey->input_dev);
|
||||
gLastKeyCode = 0;
|
||||
DBG("===========headset key release code=%d ===========\n",code);
|
||||
}
|
||||
gADValue = 0;
|
||||
gSampleTimes = 0;
|
||||
}
|
||||
}
|
||||
|
||||
static int __devinit rk28_adckey_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct rk28_hskey *hskey;
|
||||
struct input_dev *input_dev;
|
||||
int error,i,irq_num;
|
||||
struct rk2818_adckey_platform_data *pdata = pdev->dev.platform_data;
|
||||
|
||||
if (!(pdata->adc_key))
|
||||
return -1;
|
||||
|
||||
hskey = kzalloc(sizeof(struct rk28_hskey), GFP_KERNEL);
|
||||
if (hskey == NULL) {
|
||||
dev_err(&pdev->dev, "failed to allocate driver data\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
hskey->keycodes = pdata->adc_key->initKeyCode;
|
||||
|
||||
/* Create and register the input driver. */
|
||||
input_dev = input_allocate_device();
|
||||
if (!input_dev) {
|
||||
dev_err(&pdev->dev, "failed to allocate input device\n");
|
||||
error = -ENOMEM;
|
||||
goto failed_free;
|
||||
}
|
||||
|
||||
input_dev->name = pdev->name;
|
||||
input_dev->open = rk28_Hskey_open;
|
||||
input_dev->close = rk28_Hskey_close;
|
||||
input_dev->dev.parent = &pdev->dev;
|
||||
//input_dev->phys = KEY_PHYS_NAME;
|
||||
input_dev->id.vendor = 0x0001;
|
||||
input_dev->id.product = 0x0001;
|
||||
input_dev->id.version = 0x0100;
|
||||
|
||||
input_dev->keycode = hskey->keycodes;
|
||||
input_dev->keycodesize = sizeof(unsigned char);
|
||||
input_dev->keycodemax = pdata->adc_key->adc_key_cnt;
|
||||
for (i = 0; i < pdata->adc_key->adc_key_cnt; i++)
|
||||
set_bit(pdata->adc_key->initKeyCode[i], input_dev->keybit);
|
||||
clear_bit(0, input_dev->keybit);
|
||||
|
||||
hskey->input_dev = input_dev;
|
||||
input_set_drvdata(input_dev, hskey);
|
||||
|
||||
input_dev->evbit[0] = BIT_MASK(EV_KEY);
|
||||
|
||||
platform_set_drvdata(pdev, hskey);
|
||||
|
||||
phsKey = hskey;
|
||||
|
||||
/* Register the input device */
|
||||
error = input_register_device(input_dev);
|
||||
if (error) {
|
||||
dev_err(&pdev->dev, "failed to register input device\n");
|
||||
goto failed_free_dev;
|
||||
}
|
||||
|
||||
setup_timer(&hskey->timer, rk28_hskeyscan_timer, (unsigned long)(pdata->adc_key));
|
||||
hskey->timer.expires = jiffies+50;
|
||||
add_timer(&hskey->timer);
|
||||
printk(KERN_INFO "rk2818_hskey: driver initialized\n");
|
||||
return 0;
|
||||
|
||||
free_gpio_irq:
|
||||
free_irq(irq_num,NULL);
|
||||
free_gpio:
|
||||
gpio_free(pdata->adc_key->pin_playon);
|
||||
failed_free_dev:
|
||||
platform_set_drvdata(pdev, NULL);
|
||||
input_free_device(input_dev);
|
||||
failed_free:
|
||||
kfree(hskey);
|
||||
return error;
|
||||
}
|
||||
|
||||
static int __devexit rk28_adckey_remove(struct platform_device *pdev)
|
||||
{
|
||||
struct rk28_hskey *adckey = platform_get_drvdata(pdev);
|
||||
struct rk2818_adckey_platform_data *pdata = pdev->dev.platform_data;
|
||||
|
||||
input_unregister_device(adckey->input_dev);
|
||||
input_free_device(adckey->input_dev);
|
||||
platform_set_drvdata(pdev, NULL);
|
||||
kfree(adckey);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct platform_driver rk28_hskey_driver =
|
||||
{
|
||||
.probe = rk28_adckey_probe,
|
||||
.remove = __devexit_p(rk28_adckey_remove),
|
||||
.suspend = rk28_hskey_suspend,
|
||||
.resume = rk28_hskey_resume,
|
||||
.driver = {
|
||||
.name = "rk2818-hskey",
|
||||
.owner = THIS_MODULE,
|
||||
},
|
||||
};
|
||||
|
||||
int __init rk28_hskey_init(void)
|
||||
{
|
||||
return platform_driver_register(&rk28_hskey_driver);
|
||||
}
|
||||
|
||||
static void __exit rk28_hskey_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&rk28_hskey_driver);
|
||||
}
|
||||
|
||||
module_init(rk28_hskey_init);
|
||||
module_exit(rk28_hskey_exit);
|
||||
|
||||
MODULE_DESCRIPTION("rk2818 headset Key Controller Driver");
|
||||
MODULE_AUTHOR("luowei lw@rock-chips.com");
|
||||
MODULE_LICENSE("GPL");
|
||||
|
||||
@@ -96,7 +96,7 @@
|
||||
#define VIPREGNTSC 0x00000000
|
||||
#define VIPREGPAL 0x00000400
|
||||
//--------------------------
|
||||
#define CONFIG_RK28CAMERA_TR 1
|
||||
#define CONFIG_RK28CAMERA_TR 0
|
||||
#define CONFIG_RK28CAMERA_DEBUG 0
|
||||
#if (CONFIG_RK28CAMERA_TR)
|
||||
#define RK28CAMERA_TR(format, ...) printk(format, ## __VA_ARGS__)
|
||||
@@ -107,6 +107,7 @@
|
||||
#endif
|
||||
#else
|
||||
#define RK28CAMERA_TR(format, ...)
|
||||
#define RK28CAMERA_DG(format, ...)
|
||||
#endif
|
||||
|
||||
#define MIN(x,y) ((x<y) ? x: y)
|
||||
|
||||
@@ -284,6 +284,10 @@ config APANIC_PLABEL
|
||||
If your platform uses a different flash partition label for storing
|
||||
crashdumps, enter it here.
|
||||
|
||||
config STE
|
||||
bool "STE modem control driver"
|
||||
default n
|
||||
|
||||
source "drivers/misc/c2port/Kconfig"
|
||||
source "drivers/misc/eeprom/Kconfig"
|
||||
source "drivers/misc/cb710/Kconfig"
|
||||
|
||||
@@ -28,3 +28,4 @@ obj-y += eeprom/
|
||||
obj-y += cb710/
|
||||
obj-$(CONFIG_WL127X_RFKILL) += wl127x-rfkill.o
|
||||
obj-$(CONFIG_APANIC) += apanic.o
|
||||
obj-$(CONFIG_STE) += ste.o
|
||||
|
||||
203
drivers/misc/ste.c
Normal file
203
drivers/misc/ste.c
Normal file
@@ -0,0 +1,203 @@
|
||||
#include <linux/module.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/i2c.h>
|
||||
#include <linux/irq.h>
|
||||
#include <linux/gpio.h>
|
||||
#include <linux/input.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/ste.h>
|
||||
#include <linux/fs.h>
|
||||
#include <linux/uaccess.h>
|
||||
#include <linux/miscdevice.h>
|
||||
#include <linux/circ_buf.h>
|
||||
#include <linux/interrupt.h>
|
||||
#include <mach/spi_fpga.h>
|
||||
#include <linux/delay.h>
|
||||
|
||||
#if 1
|
||||
#define D(x...) printk(x)
|
||||
#else
|
||||
#define D(x...)
|
||||
#endif
|
||||
|
||||
static int misc_opened;
|
||||
|
||||
#define AP_TD_UNDEFINED_GBIN5 FPGA_PIO2_02
|
||||
#define AP_RESET_TD FPGA_PIO2_04
|
||||
#define AP_SHUTDOWN_TD_PMU FPGA_PIO2_05
|
||||
#define AP_PW_EN_TD FPGA_PIO2_03
|
||||
|
||||
#define PIN_BPSEND_ACK RK2818_PIN_PE0
|
||||
#define PIN_APSEND_ACK RK2818_PIN_PF7
|
||||
|
||||
static int bp_power_on(void)
|
||||
{
|
||||
int ret=0;
|
||||
|
||||
ret = gpio_request(AP_TD_UNDEFINED_GBIN5, NULL);
|
||||
if (ret) {
|
||||
printk("%s:failed to request fpga s %d\n",__FUNCTION__,__LINE__);
|
||||
goto err;
|
||||
}
|
||||
ret = gpio_request(AP_RESET_TD, NULL);
|
||||
if (ret) {
|
||||
printk("%s:failed to request fpga s %d\n",__FUNCTION__,__LINE__);
|
||||
goto err0;
|
||||
}
|
||||
|
||||
|
||||
ret = gpio_request(AP_SHUTDOWN_TD_PMU, NULL);
|
||||
if (ret) {
|
||||
printk("%s:failed to request fpga %d\n",__FUNCTION__,__LINE__);
|
||||
goto err1;
|
||||
}
|
||||
|
||||
ret = gpio_request(AP_PW_EN_TD, NULL);
|
||||
if (ret) {
|
||||
printk("%s:failed to request fpga %d\n",__FUNCTION__,__LINE__);
|
||||
goto err2;
|
||||
}
|
||||
|
||||
gpio_set_value(AP_TD_UNDEFINED_GBIN5, 1);
|
||||
gpio_direction_output(AP_TD_UNDEFINED_GBIN5, 1);
|
||||
gpio_direction_input(AP_RESET_TD);
|
||||
|
||||
gpio_set_value(AP_SHUTDOWN_TD_PMU, 0);
|
||||
gpio_direction_output(AP_SHUTDOWN_TD_PMU, 0);
|
||||
|
||||
gpio_set_value(AP_PW_EN_TD, 0);
|
||||
gpio_direction_output(AP_PW_EN_TD, 0);
|
||||
mdelay(1);
|
||||
gpio_set_value(AP_PW_EN_TD, 1);
|
||||
mdelay(1200);
|
||||
gpio_set_value(AP_PW_EN_TD, 0);
|
||||
|
||||
return true;
|
||||
err2:
|
||||
gpio_free(AP_SHUTDOWN_TD_PMU);
|
||||
err1:
|
||||
gpio_free(AP_RESET_TD);
|
||||
err0:
|
||||
gpio_free(AP_TD_UNDEFINED_GBIN5);
|
||||
err:
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
static int bp_power_off(void)
|
||||
{
|
||||
D("+++--++++++%s_________ \r\n",__FUNCTION__);
|
||||
|
||||
gpio_set_value(AP_TD_UNDEFINED_GBIN5, 0);
|
||||
|
||||
gpio_set_value(AP_PW_EN_TD, 0);
|
||||
//gpio_direction_output(AP_PW_EN_TD, 0);
|
||||
mdelay(1);
|
||||
gpio_set_value(AP_PW_EN_TD, 1);
|
||||
mdelay(1200);
|
||||
gpio_set_value(AP_PW_EN_TD, 0);
|
||||
|
||||
mdelay(5000);
|
||||
gpio_set_value(AP_SHUTDOWN_TD_PMU, 1);
|
||||
mdelay(1200);
|
||||
// gpio_free(AP_PW_EN_TD);
|
||||
D("++++--+++++%s ok_________\r\n",__FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
//add end
|
||||
|
||||
static int ste_open(struct inode *inode, struct file *file)
|
||||
{
|
||||
D("%s\n", __func__);
|
||||
if (misc_opened)
|
||||
return -EBUSY;
|
||||
misc_opened = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ste_release(struct inode *inode, struct file *file)
|
||||
{
|
||||
D("%s\n", __func__);
|
||||
misc_opened = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ste_ioctl(struct inode *inode,struct file *file, unsigned int cmd, unsigned long arg)
|
||||
{
|
||||
int val;
|
||||
D("%s cmd %d\n", __func__, _IOC_NR(cmd));
|
||||
switch (cmd) {
|
||||
case STE_IOCTL_EN_APSEND_ACK:
|
||||
D("%s:STE_IOCTL_EN_APSEND_ACK\n");
|
||||
gpio_direction_output(PIN_APSEND_ACK,GPIO_LOW);
|
||||
msleep(50);
|
||||
gpio_direction_output(PIN_APSEND_ACK,GPIO_HIGH);
|
||||
msleep(50);
|
||||
break;
|
||||
case STE_IOCTL_GET_ACK:
|
||||
val = gpio_get_value(PIN_BPSEND_ACK);
|
||||
D("%s:STE_IOCTL_GET_ACK pin status is %d\n",__func__,val);
|
||||
return put_user(val, (unsigned long __user *)arg);
|
||||
break;
|
||||
case STE_IOCTL_POWER_ON:
|
||||
D("%s:STE_IOCTL_POWER_ON\n",__func__);
|
||||
bp_power_on();
|
||||
break;
|
||||
case STE_IOCTL_POWER_OFF:
|
||||
D("%s:STE_IOCTL_POWER_OFF\n",__func__);
|
||||
bp_power_off();
|
||||
break;
|
||||
default:
|
||||
pr_err("%s: invalid cmd %d\n", __func__, _IOC_NR(cmd));
|
||||
return -EINVAL;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct file_operations ste_fops = {
|
||||
.owner = THIS_MODULE,
|
||||
.open = ste_open,
|
||||
.release = ste_release,
|
||||
.ioctl = ste_ioctl
|
||||
};
|
||||
|
||||
static struct miscdevice ste_misc = {
|
||||
.minor = MISC_DYNAMIC_MINOR,
|
||||
.name = STE_NAME,
|
||||
.fops = &ste_fops
|
||||
};
|
||||
|
||||
static int ste_probe(struct platform_device *pdev)
|
||||
{
|
||||
int rc = -EIO;
|
||||
D("%s-----------\n",__FUNCTION__);
|
||||
|
||||
rc = misc_register(&ste_misc);
|
||||
if (rc < 0) {
|
||||
pr_err("%s: could not register misc device\n", __func__);
|
||||
// goto err_unregister_input_device;
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
static struct platform_driver ste_driver = {
|
||||
.probe = ste_probe,
|
||||
.driver = {
|
||||
.name = "ste",
|
||||
.owner = THIS_MODULE
|
||||
},
|
||||
};
|
||||
|
||||
static int __init ste_init(void)
|
||||
{
|
||||
return platform_driver_register(&ste_driver);
|
||||
}
|
||||
|
||||
static void __exit ste_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&ste_driver);
|
||||
}
|
||||
|
||||
module_init(ste_init);
|
||||
module_exit(ste_exit);
|
||||
@@ -26,7 +26,7 @@
|
||||
#define RTC_RATE 100 * 1000
|
||||
#define S35392_TEST 0
|
||||
|
||||
#if 1
|
||||
#if 0
|
||||
#define DBG(x...) printk(x)
|
||||
#else
|
||||
#define DBG(x...)
|
||||
@@ -56,7 +56,7 @@ static int s35392a_set_reg(struct s35392a *s35392a, const char reg, char *buf, i
|
||||
|
||||
ret = i2c_transfer(client->adapter,&msg,1);
|
||||
for(i=0;i<len;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
return ret;
|
||||
|
||||
}
|
||||
@@ -219,11 +219,11 @@ static int s35392a_set_datetime(struct i2c_client *client, struct rtc_time *tm)
|
||||
|
||||
/* This chip expects the bits of each byte to be in reverse order */
|
||||
for(i=0;i<7;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
for (i = 0; i < 7; ++i)
|
||||
buf[i] = bitrev8(buf[i]);
|
||||
for(i=0;i<7;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
err = s35392a_set_reg(s35392a, S35392A_CMD_TIME1, buf, sizeof(buf));
|
||||
|
||||
return err;
|
||||
@@ -239,12 +239,12 @@ static int s35392a_get_datetime(struct i2c_client *client, struct rtc_time *tm)
|
||||
if (err < 0)
|
||||
return err;
|
||||
for(i=0;i<7;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
/* This chip returns the bits of each byte in reverse order */
|
||||
for (i = 0; i < 7; ++i)
|
||||
buf[i] = bitrev8(buf[i]);
|
||||
for(i=0;i<7;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
tm->tm_sec = bcd2bin(buf[S35392A_BYTE_SECS]);
|
||||
tm->tm_min = bcd2bin(buf[S35392A_BYTE_MINS]);
|
||||
tm->tm_hour = s35392a_reg2hr(s35392a, buf[S35392A_BYTE_HOURS]);
|
||||
@@ -272,11 +272,11 @@ static int s35392a_i2c_read_alarm(struct i2c_client *client, struct rtc_wkalrm
|
||||
if(err < 0)
|
||||
return err;
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
for(i = 0;i < 3;++i)
|
||||
buf[i] = bitrev8(buf[i]);
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
tm->time.tm_wday = -1;
|
||||
tm->time.tm_hour = -1;
|
||||
tm->time.tm_min = -1;
|
||||
@@ -330,11 +330,11 @@ static int s35392a_i2c_set_alarm(struct i2c_client *client, struct rtc_wkalrm *
|
||||
buf[S35392A_ALARM_MINS] = tm->time.tm_min >= 0?
|
||||
bin2bcd(tm->time.tm_min) | S35392A_ALARM_ENABLE:0;
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
for(i = 0;i < 3;++i)
|
||||
buf[i] = bitrev8(buf[i]);
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
if(tm->enabled)
|
||||
{
|
||||
data = 0x00;
|
||||
@@ -346,7 +346,7 @@ static int s35392a_i2c_set_alarm(struct i2c_client *client, struct rtc_wkalrm *
|
||||
data = 0x02;
|
||||
s35392a_set_reg(s35392a, S35392A_CMD_STATUS2, &data, 1);
|
||||
s35392a_get_reg(s35392a, S35392A_CMD_STATUS2, &data, 1);
|
||||
printk("data = 0x%x\n",data);
|
||||
DBG("data = 0x%x\n",data);
|
||||
err = s35392a_set_reg(s35392a, S35392A_CMD_INT2, buf, sizeof(buf));
|
||||
return err;
|
||||
}
|
||||
@@ -370,11 +370,11 @@ static int s35392a_i2c_read_alarm0(struct i2c_client *client, struct rtc_wkalrm
|
||||
if(err < 0)
|
||||
return err;
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
for(i = 0;i < 3;++i)
|
||||
buf[i] = bitrev8(buf[i]);
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
tm->time.tm_wday = -1;
|
||||
tm->time.tm_hour = -1;
|
||||
tm->time.tm_min = -1;
|
||||
@@ -428,11 +428,11 @@ static int s35392a_i2c_set_alarm0(struct i2c_client *client, struct rtc_wkalrm
|
||||
buf[S35392A_ALARM_MINS] = tm->time.tm_min >= 0?
|
||||
bin2bcd(tm->time.tm_min) | S35392A_ALARM_ENABLE:0;
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
for(i = 0;i < 3;++i)
|
||||
buf[i] = bitrev8(buf[i]);
|
||||
for(i=0;i<3;i++)
|
||||
printk("buf[%d]=0x%x\n",i,buf[i]);
|
||||
DBG("buf[%d]=0x%x\n",i,buf[i]);
|
||||
if(tm->enabled)
|
||||
{
|
||||
data = 0x00;
|
||||
@@ -444,7 +444,7 @@ static int s35392a_i2c_set_alarm0(struct i2c_client *client, struct rtc_wkalrm
|
||||
data = 0x02;
|
||||
s35392a_set_reg(s35392a, S35392A_CMD_STATUS2, &data, 1);
|
||||
s35392a_get_reg(s35392a, S35392A_CMD_STATUS2, &data, 1);
|
||||
printk("data = 0x%x\n",data);
|
||||
DBG("data = 0x%x\n",data);
|
||||
err = s35392a_set_reg(s35392a, S35392A_CMD_INT1, buf, sizeof(buf));
|
||||
return err;
|
||||
}
|
||||
@@ -743,7 +743,7 @@ static void s35392a_work_func(struct work_struct *work)
|
||||
struct s35392a *s35392a = container_of(work, struct s35392a, work);
|
||||
struct i2c_client *client = s35392a->client;
|
||||
|
||||
printk("\n@@@@@@@@@@@rtc_wakeup_irq@@@@@@@@@@@@@\n");
|
||||
DBG("\n@@@@@@@@@@@rtc_wakeup_irq@@@@@@@@@@@@@\n");
|
||||
|
||||
char data = 0x00;
|
||||
s35392a_get_reg(s35392a, S35392A_CMD_STATUS2, &data, 1);
|
||||
@@ -751,7 +751,7 @@ static void s35392a_work_func(struct work_struct *work)
|
||||
s35392a_set_reg(s35392a, S35392A_CMD_STATUS2, &data, 1);
|
||||
s35392a_get_reg(s35392a, S35392A_CMD_STATUS2, &data, 1);
|
||||
|
||||
printk("\n@@@@@@@@@@@rtc_wakeup_irq@@@@@@@@@@@@@\n");
|
||||
DBG("\n@@@@@@@@@@@rtc_wakeup_irq@@@@@@@@@@@@@\n");
|
||||
|
||||
enable_irq(client->irq);
|
||||
}
|
||||
@@ -774,7 +774,7 @@ static int s35392a_probe(struct i2c_client *client,
|
||||
struct rtc_time tm;
|
||||
char buf[1];
|
||||
|
||||
printk("@@@@@%s:%d@@@@@\n",__FUNCTION__,__LINE__);
|
||||
DBG("@@@@@%s:%d@@@@@\n",__FUNCTION__,__LINE__);
|
||||
if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
|
||||
err = -ENODEV;
|
||||
goto exit;
|
||||
@@ -843,7 +843,7 @@ static int s35392a_probe(struct i2c_client *client,
|
||||
|
||||
if(err = request_irq(client->irq, s35392a_wakeup_irq,IRQF_TRIGGER_LOW,NULL,s35392a) <0)
|
||||
{
|
||||
printk("unable to request rtc irq\n");
|
||||
DBG("unable to request rtc irq\n");
|
||||
goto exit_dummy;
|
||||
}
|
||||
}
|
||||
@@ -854,7 +854,7 @@ static int s35392a_probe(struct i2c_client *client,
|
||||
|
||||
if(err = request_irq(client->irq, s35392a_wakeup_irq,IRQF_TRIGGER_HIGH,NULL,s35392a) <0)
|
||||
{
|
||||
printk("unable to request rtc irq\n");
|
||||
DBG("unable to request rtc irq\n");
|
||||
goto exit_dummy;
|
||||
}
|
||||
}
|
||||
@@ -871,7 +871,7 @@ static int s35392a_probe(struct i2c_client *client,
|
||||
}
|
||||
#endif
|
||||
|
||||
printk("@@@@@%s:%d@@@@@\n",__FUNCTION__,__LINE__);
|
||||
DBG("@@@@@%s:%d@@@@@\n",__FUNCTION__,__LINE__);
|
||||
return 0;
|
||||
|
||||
exit_dummy:
|
||||
@@ -916,7 +916,7 @@ static struct i2c_driver s35392a_driver = {
|
||||
|
||||
static int __init s35392a_rtc_init(void)
|
||||
{
|
||||
printk("@@@@@%s:%d@@@@@\n",__FUNCTION__,__LINE__);
|
||||
DBG("@@@@@%s:%d@@@@@\n",__FUNCTION__,__LINE__);
|
||||
return i2c_add_driver(&s35392a_driver);
|
||||
}
|
||||
|
||||
|
||||
@@ -23,6 +23,11 @@
|
||||
#include "timed_output.h"
|
||||
#include "timed_gpio.h"
|
||||
|
||||
#if defined(CONFIG_MACH_RAHO)||defined(CONFIG_MACH_RAHO_0928)
|
||||
#define GPIO_TYPE 1 //ʹ<><CAB9>FPGA<47><41>չ<EFBFBD><D5B9>IO<49><4F><EFBFBD><EFBFBD>ʹ<EFBFBD><CAB9><EFBFBD>ж<EFBFBD><D0B6>ڲ<EFBFBD>ֱ<EFBFBD>Ӳ<EFBFBD><D3B2><EFBFBD>IO
|
||||
#else
|
||||
#define GPIO_TYPE 0
|
||||
#endif
|
||||
|
||||
struct timed_gpio_data {
|
||||
struct timed_output_dev dev;
|
||||
@@ -31,14 +36,30 @@ struct timed_gpio_data {
|
||||
unsigned gpio;
|
||||
int max_timeout;
|
||||
u8 active_low;
|
||||
#if (GPIO_TYPE == 1)
|
||||
struct work_struct timed_gpio_work;
|
||||
#endif
|
||||
};
|
||||
|
||||
#if (GPIO_TYPE == 1)
|
||||
static void timed_gpio_work_handler(struct work_struct *work)
|
||||
{
|
||||
struct timed_gpio_data *data =
|
||||
container_of(work, struct timed_gpio_data, timed_gpio_work);
|
||||
gpio_direction_output(data->gpio, data->active_low ? 1 : 0);
|
||||
}
|
||||
#endif
|
||||
|
||||
static enum hrtimer_restart gpio_timer_func(struct hrtimer *timer)
|
||||
{
|
||||
struct timed_gpio_data *data =
|
||||
container_of(timer, struct timed_gpio_data, timer);
|
||||
|
||||
|
||||
#if (GPIO_TYPE == 0)
|
||||
gpio_direction_output(data->gpio, data->active_low ? 1 : 0);
|
||||
#else
|
||||
schedule_work(&data->timed_gpio_work);
|
||||
#endif
|
||||
return HRTIMER_NORESTART;
|
||||
}
|
||||
|
||||
@@ -59,9 +80,8 @@ static void gpio_enable(struct timed_output_dev *dev, int value)
|
||||
{
|
||||
struct timed_gpio_data *data =
|
||||
container_of(dev, struct timed_gpio_data, dev);
|
||||
unsigned long flags;
|
||||
|
||||
spin_lock_irqsave(&data->lock, flags);
|
||||
//unsigned long flags;
|
||||
//spin_lock_irqsave(&data->lock, flags);
|
||||
|
||||
/* cancel previous timer and set GPIO according to value */
|
||||
hrtimer_cancel(&data->timer);
|
||||
@@ -76,7 +96,7 @@ static void gpio_enable(struct timed_output_dev *dev, int value)
|
||||
HRTIMER_MODE_REL);
|
||||
}
|
||||
|
||||
spin_unlock_irqrestore(&data->lock, flags);
|
||||
//spin_unlock_irqrestore(&data->lock, flags);
|
||||
}
|
||||
|
||||
static int timed_gpio_probe(struct platform_device *pdev)
|
||||
@@ -126,7 +146,9 @@ static int timed_gpio_probe(struct platform_device *pdev)
|
||||
gpio_dat->active_low = cur_gpio->active_low;
|
||||
gpio_direction_output(gpio_dat->gpio, gpio_dat->active_low);
|
||||
}
|
||||
|
||||
#if (GPIO_TYPE == 1)
|
||||
INIT_WORK(&gpio_dat->timed_gpio_work, timed_gpio_work_handler);
|
||||
#endif
|
||||
platform_set_drvdata(pdev, gpio_data);
|
||||
|
||||
return 0;
|
||||
|
||||
14
include/linux/ste.h
Normal file
14
include/linux/ste.h
Normal file
@@ -0,0 +1,14 @@
|
||||
#include <linux/types.h>
|
||||
#include <linux/ioctl.h>
|
||||
|
||||
#define STE_IOCTL_MAGIC 'd'
|
||||
#define STE_IOCTL_GET_ACK \
|
||||
_IOR(STE_IOCTL_MAGIC, 1, int *)
|
||||
#define STE_IOCTL_EN_APSEND_ACK \
|
||||
_IOW(STE_IOCTL_MAGIC, 2, int *)
|
||||
#define STE_IOCTL_POWER_ON \
|
||||
_IOW(STE_IOCTL_MAGIC, 3, int *)
|
||||
#define STE_IOCTL_POWER_OFF \
|
||||
_IOW(STE_IOCTL_MAGIC, 4, int *)
|
||||
|
||||
#define STE_NAME "STE"
|
||||
Reference in New Issue
Block a user