コード例 #1
0
static irqreturn_t msm_ts_irq(int irq, void *dev_id)
{
    struct msm_ts *ts = dev_id;
    struct msm_ts_platform_data *pdata = ts->pdata;

    uint32_t tssc_avg12, tssc_avg34, tssc_status, tssc_ctl;
    int x, y, z1, z2;
    int was_down;
    int down;

    tssc_ctl = tssc_readl(ts, TSSC_CTL);
    tssc_status = tssc_readl(ts, TSSC_STATUS);
    tssc_avg12 = tssc_readl(ts, TSSC_AVG_12);
    tssc_avg34 = tssc_readl(ts, TSSC_AVG_34);

    setup_next_sample(ts);

    x = tssc_avg12 & 0xffff;
    y = tssc_avg12 >> 16;
    z1 = tssc_avg34 & 0xffff;
    z2 = tssc_avg34 >> 16;

    /* invert the inputs if necessary */
    if (pdata->inv_x) x = pdata->inv_x - x;
    if (pdata->inv_y) y = pdata->inv_y - y;
    if (x < 0) x = 0;
    if (y < 0) y = 0;

    down = !(tssc_ctl & TSSC_CTL_PENUP_IRQ);
    was_down = ts->ts_down;
    ts->ts_down = down;

    /* no valid data */
    if (down && !(tssc_ctl & TSSC_CTL_DATA_FLAG))
        return IRQ_HANDLED;

    if (msm_tsdebug & 2)
        printk("%s: down=%d, x=%d, y=%d, z1=%d, z2=%d, status %x\n",
               __func__, down, x, y, z1, z2, tssc_status);

    if (!was_down && down) {
        struct ts_virt_key *vkey = NULL;

        if (pdata->vkeys_y && (y > pdata->virt_y_start))
            vkey = find_virt_key(ts, pdata->vkeys_y, x);
        if (!vkey && ts->pdata->vkeys_x && (x > pdata->virt_x_start))
            vkey = find_virt_key(ts, pdata->vkeys_x, y);

        if (vkey) {
            WARN_ON(ts->vkey_down != NULL);
            if(msm_tsdebug)
                printk("%s: virtual key down %d\n", __func__,
                       vkey->key);
            ts->vkey_down = vkey;
            input_report_key(ts->input_dev, vkey->key, 1);
            input_sync(ts->input_dev);
            return IRQ_HANDLED;
        }
    } else if (ts->vkey_down != NULL) {
        if (!down) {
            if(msm_tsdebug)
                printk("%s: virtual key up %d\n", __func__,
                       ts->vkey_down->key);
            input_report_key(ts->input_dev, ts->vkey_down->key, 0);
            input_sync(ts->input_dev);
            ts->vkey_down = NULL;
        }
        return IRQ_HANDLED;
    }

    if (down) {
        input_report_abs(ts->input_dev, ABS_X, x);
        input_report_abs(ts->input_dev, ABS_Y, y);
        input_report_abs(ts->input_dev, ABS_PRESSURE, z1);
    }
    input_report_key(ts->input_dev, BTN_TOUCH, down);
    input_sync(ts->input_dev);

    return IRQ_HANDLED;
}
コード例 #2
0
ファイル: bcm_gpio_keypad.c プロジェクト: kzlin129/tt-gpl
/****************************************************************************f
*
*   Scan the matrix, and generate event for changes.
*
***************************************************************************/
static void keypad_scan( int gpio_pin, struct CBLK *bcm_kp )
{
	unsigned int stat;
	int r, gpio_c, value;
    int c = 0;

    r = elementExistInArray( gpio_pin, bcm_kp->row_count , bcm_kp->keyRowArray );
    stat = gpio_get_value(gpio_pin);
    if(stat)
    {
        /* At this point we know that the some key was released. So no point in scanning the 
        Matrix. Just report the last pressed key on same GPIO as released. */  
        
        /* Handle if its a Direct key release*/
        if(( bcm_kp->direct_key_col_index != -1 ) && ( bcm_kp->keycode[SCANCODE(r,bcm_kp->direct_key_col_index)] )) 
        {
            input_report_key(bcm_kp->input_dev, bcm_kp->keycode[SCANCODE(r,bcm_kp->direct_key_col_index)], !stat);         
            input_sync( bcm_kp->input_dev );
        }

        /* Handle Matrix Key Release */
        else
        {
            for(c=0;c< bcm_kp->col_count;c++)
            {
                if( test_bit( SCANCODE(r,c), bcm_kp->prevDown ) )
                {
                    input_report_key(bcm_kp->input_dev, bcm_kp->keycode[SCANCODE(r,c)], !stat);
                    input_sync( bcm_kp->input_dev );                    
                    change_bit( SCANCODE(r,c), bcm_kp->prevDown );
                    BCMKP_DBG(KERN_DEBUG "Key released r=%d c=%d..\n", r, c);
                } 
            }            
        }            
    }
    
    else {
        /* The Key is presses, so scan the Matrix */
        //Now we have the GPIO row that cause the interrupt 
        if(( bcm_kp->direct_key_col_index != -1 ) && ( bcm_kp->keycode[SCANCODE(r,bcm_kp->direct_key_col_index)] ))
        {
            /* The Key is a Direct Key */
            input_report_key(bcm_kp->input_dev, bcm_kp->keycode[SCANCODE(r,bcm_kp->direct_key_col_index)], !stat);            
            BCMKP_DBG(KERN_DEBUG "GPIO %d row press found Direct Key..\n", gpio_pin);
        }
        
        else{
            //Now set all Col as High
            for(c=0;c< bcm_kp->col_count;c++)
            {
                gpio_c = bcm_kp->keyColArray[c];
                if( gpio_c != BCM_NO_COLUMN )
                    gpio_set_value( gpio_c, 1 );
            }
            
            for(c=0;c< bcm_kp->col_count;c++)
            {
                gpio_c = bcm_kp->keyColArray[c];
                if( gpio_c == BCM_NO_COLUMN )
                    continue;
                gpio_set_value( gpio_c, 0 ); 
                value = gpio_get_value(gpio_pin); 
                gpio_set_value( gpio_c, 1 );
                
                if( !value )  //Found the Key
                {
                    if( bcm_kp->keycode[SCANCODE(r,c)] && !test_bit( SCANCODE(r,c), bcm_kp->prevDown ) )
                    {
                        /* report status to input-subsystem */
                        input_report_key(bcm_kp->input_dev, bcm_kp->keycode[SCANCODE(r,c)], !value);
                        input_sync( bcm_kp->input_dev );
                        change_bit( SCANCODE(r,c), bcm_kp->prevDown );
                        BCMKP_DBG(KERN_DEBUG "Key Pressed r=%d c=%d..\n", r, c);
                        break;
                    }
                }
                
            }
            
             //Now restore all the Col as Low for next interrupt
            for(c=0;c< bcm_kp->col_count;c++)
            {
                gpio_c = bcm_kp->keyColArray[c];
                if( gpio_c != BCM_NO_COLUMN )
                    gpio_set_value( gpio_c, 0 );
            }           
            
        }
	}
	return;
}
static irqreturn_t touchkey_interrupt(int irq, void *dev_id)
{
	struct touchkey_i2c *tkey_i2c = dev_id;
	u8 data[18];
	int ret;
	int retry = 10;
	int keycode_type = 0;
	int pressed;

#if 0
	if (gpio_get_value(_3_GPIO_TOUCH_INT)) {
		pr_debug("[TouchKey] Unknown state.\n", __func__);
		return IRQ_HANDLED;
	}
#endif

	set_touchkey_debug('a');

#ifdef CONFIG_CPU_FREQ
	/* set_dvfs_target_level(LEV_800MHZ); */
#endif

	retry = 3;
	while (retry--) {
#if defined(CONFIG_TARGET_LOCALE_NA) || defined(CONFIG_MACH_Q1_BD)\
	 || defined(CONFIG_MACH_C1)
		ret = i2c_touchkey_read(tkey_i2c->client,
				KEYCODE_REG, data, 18);
#else
		ret = i2c_touchkey_read(tkey_i2c->client,
				KEYCODE_REG, data, 10);
#endif
		if (!ret)
			break;
		else {
			pr_debug("[TouchKey] i2c read failed, ret:%d, retry: %d\n",
			       ret, retry);
			continue;
		}
	}
	if (ret < 0)
		return IRQ_HANDLED;

#if defined(CONFIG_TARGET_LOCALE_NA)
#if defined(CONFIG_MACH_C1_NA_SPR_EPIC2_REV00)
	menu_sensitivity = data[11];
	home_sensitivity = data[13];
	search_sensitivity = data[15];
	back_sensitivity = data[17];
#else
	if (tkey_i2c->module_ver >= 8) {
		menu_sensitivity = data[17];
		home_sensitivity = data[15];
		search_sensitivity = data[11];
		back_sensitivity = data[13];
	} else {
		menu_sensitivity = data[6];
		home_sensitivity = data[7];
		search_sensitivity = data[8];
		back_sensitivity = data[9];
	}
#endif
#elif defined(CONFIG_MACH_Q1_BD) || defined(CONFIG_MACH_C1)
	menu_sensitivity = data[13];
	back_sensitivity = data[11];
#else
	menu_sensitivity = data[7];
	back_sensitivity = data[9];
#endif				/* CONFIG_TARGET_LOCALE_NA  */

	set_touchkey_debug(data[0]);

	keycode_type = (data[0] & TK_BIT_KEYCODE);
	pressed = !(data[0] & TK_BIT_PRESS_EV);

	if (keycode_type <= 0 || keycode_type >= touchkey_count) {
		pr_debug("[Touchkey] keycode_type err\n");
		return IRQ_HANDLED;
	}

	if (pressed) {
		set_touchkey_debug('P');
    }

	if (get_tsp_status() && pressed)
		pr_debug("[TouchKey] touchkey pressed"
		       " but don't send event because touch is pressed.\n");
	else {
		input_report_key(touchkey_driver->input_dev,
				 touchkey_keycode[keycode_type], pressed);
		input_sync(touchkey_driver->input_dev);
		/* printk(KERN_DEBUG "[TouchKey] keycode:%d pressed:%d\n",
		   touchkey_keycode[keycode_index], pressed); */
	}

	if (keycode_type == 1)
		printk(KERN_DEBUG "search key sensitivity = %d\n",
		       search_sensitivity);
	if (keycode_type == 2)
		pr_debug("back key sensitivity = %d\n",
		       back_sensitivity);
#ifdef CONFIG_TARGET_LOCALE_NA
	if (keycode_type == 3)
		pr_debug("home key sensitivity = %d\n",
		       home_sensitivity);
	if (keycode_type == 4)
		pr_debug("menu key sensitivity = %d\n",
		       menu_sensitivity);
#endif

	set_touchkey_debug('A');
	return IRQ_HANDLED;
}
コード例 #4
0
ファイル: front.c プロジェクト: Audioniek/driver
void scan_key(void)
{
	int i, j;
	u32 key_data = 0;
	unsigned char key_buf[5];

	memset(key_buf, 0, sizeof(key_buf));

	command(0x42);                  /*command2 read key data to Display increment mode*/

	stpio_set_pin(kfront->data, 1);

	for (i = 0; i < 5; i++)
	{
		for (j = 0; j < 8; j++)
		{
			stpio_set_pin(kfront->clk, 1);
			delay(1);
			stpio_set_pin(kfront->clk, 0);
			delay(1);
			if (stpio_get_pin(kfront->data))
			{
				key_buf[i] |= (1 << j);
			}
		}
	}

#if 0
	for (i = 0; i < 5; i++)
	{
		for (j = 0; j < 8; j++)
		{
			dprintk("%d ", (key_buf[i] >> j) & 0x01);
		}
		dprintk("\n");
	}
	dprintk("\n");
#endif

	stpio_set_pin(kfront->clk, 1);

	/*	parse key	*/
	if (key_buf[0] & 0x01)			/*	exit		*/
		key_data = FRONT_EXIT;
	else if (key_buf[0] & 0x08)		/*	ok		*/
		key_data = FRONT_OK;
	else if (key_buf[1] & 0x01)		/*	vol+		*/
		key_data = FRONT_VolUp;
	else if (key_buf[1] & 0x08)		/*	vol-		*/
		key_data = FRONT_VolDn;
	else if (key_buf[2] & 0x01)		/*	power	*/
		key_data = FRONT_STBY;
	else if (key_buf[2] & 0x08)		/*	ch-		*/
		key_data = FRONT_PgDn;
	else if (key_buf[3] & 0x01)		/*	menu	*/
		key_data = FRONT_Menu;
	else if (key_buf[3] & 0x08)		/*	ch+		*/
		key_data = FRONT_PgUp;

	if (key_data)
	{
		int key;
#ifdef REPEAT_KEY_SUPPORT
#ifdef REPEAT_DEACCEL_SUPPORT
		if (prev_key_data != key_data)
			repeat_key_count = 0;

		repeat_key_count++;
#endif
		if (is_repeat_key(key_data))
		{
#ifdef REPEAT_DEACCEL_SUPPORT
			if (repeat_key_count > 1 && repeat_key_count <= MSEC_TO_LOOP_CNT(500))
				return;
#endif
		}
		else
		{
			if (prev_key_data == key_data)
				return;
		}

		prev_key_data = key_data;
		prev_loop_count = cur_loop_count;
#endif

		// event subsystem passing
		key = translate_fp_key(key_data, 5);
		if (key)
		{
			input_report_key(fp_button_dev, key, 1);
			input_sync(fp_button_dev);
			msleep(100);
			input_report_key(fp_button_dev, key, 0);
			input_sync(fp_button_dev);
			//FIXME: Add delay to not report one key press ducplicated
		}

		DVB_RINGBUFFER_WRITE_BYTE(&ci_rbuffer, key_data);
		wake_up_interruptible(&ci_rbuffer.queue);
	}
	else
	{
#ifdef REPEAT_KEY_SUPPORT
		/*	delete chattering	*/
		if ((prev_loop_count + MSEC_TO_LOOP_CNT(200)) <= cur_loop_count)
		{
			prev_key_data = 0;
#ifdef REPEAT_DEACCEL_SUPPORT
			repeat_key_count = 0;
#endif
		}
#endif
	}
}
コード例 #5
0
/* report trackpad data as logical trackpad state */
static int report_tp_state(struct bcm5974 *dev, int size)
{
	const struct bcm5974_config *c = &dev->cfg;
	const struct tp_finger *f;
	struct input_dev *input = dev->input;
	int raw_p, raw_w, raw_x, raw_y, raw_n, i;
	int ptest, origin, ibt = 0, nmin = 0, nmax = 0;
	int abs_p = 0, abs_w = 0, abs_x = 0, abs_y = 0;

	if (size < c->tp_offset || (size - c->tp_offset) % SIZEOF_FINGER != 0)
		return -EIO;

	/* finger data, le16-aligned */
	f = (const struct tp_finger *)(dev->tp_data + c->tp_offset);
	raw_n = (size - c->tp_offset) / SIZEOF_FINGER;

	/* always track the first finger; when detached, start over */
	if (raw_n) {

		/* report raw trackpad data */
		for (i = 0; i < raw_n; i++)
			report_finger_data(input, c, &f[i]);

		raw_p = raw2int(f->force_major);
		raw_w = raw2int(f->size_major);
		raw_x = raw2int(f->abs_x);
		raw_y = raw2int(f->abs_y);

		dprintk(9,
			"bcm5974: "
			"raw: p: %+05d w: %+05d x: %+05d y: %+05d n: %d\n",
			raw_p, raw_w, raw_x, raw_y, raw_n);

		ptest = int2bound(&c->p, raw_p);
		origin = raw2int(f->origin);

		/* while tracking finger still valid, count all fingers */
		if (ptest > PRESSURE_LOW && origin) {
			abs_p = ptest;
			abs_w = int2bound(&c->w, raw_w);
			abs_x = int2bound(&c->x, raw_x - c->x.devmin);
			abs_y = int2bound(&c->y, c->y.devmax - raw_y);
			while (raw_n--) {
				ptest = int2bound(&c->p,
						  raw2int(f->force_major));
				if (ptest > PRESSURE_LOW)
					nmax++;
				if (ptest > PRESSURE_HIGH)
					nmin++;
				f++;
			}
		}
	}

	/* set the integrated button if applicable */
	if (c->tp_type == TYPE2)
		ibt = raw2int(dev->tp_data[BUTTON_TYPE2]);

	if (dev->fingers < nmin)
		dev->fingers = nmin;
	if (dev->fingers > nmax)
		dev->fingers = nmax;

	input_report_key(input, BTN_TOUCH, dev->fingers > 0);
	input_report_key(input, BTN_TOOL_FINGER, dev->fingers == 1);
	input_report_key(input, BTN_TOOL_DOUBLETAP, dev->fingers == 2);
	input_report_key(input, BTN_TOOL_TRIPLETAP, dev->fingers == 3);
	input_report_key(input, BTN_TOOL_QUADTAP, dev->fingers > 3);

	input_report_abs(input, ABS_PRESSURE, abs_p);
	input_report_abs(input, ABS_TOOL_WIDTH, abs_w);

	if (abs_p) {
		input_report_abs(input, ABS_X, abs_x);
		input_report_abs(input, ABS_Y, abs_y);

		dprintk(8,
			"bcm5974: abs: p: %+05d w: %+05d x: %+05d y: %+05d "
			"nmin: %d nmax: %d n: %d ibt: %d\n", abs_p, abs_w,
			abs_x, abs_y, nmin, nmax, dev->fingers, ibt);

	}

	/* type 2 reports button events via ibt only */
	if (c->tp_type == TYPE2)
		input_report_key(input, BTN_LEFT, ibt);

	input_sync(input);

	return 0;
}
コード例 #6
0
int wacom_i2c_coord(struct wacom_i2c *wac_i2c)
{
	bool prox = false;
	int ret = 0;
	u8 *data;
	int rubber, stylus;
	static u16 x, y, pressure;
	static u16 tmp;
	int rdy = 0;

	data = wac_i2c->wac_feature->data;
	ret = i2c_master_recv(wac_i2c->client, data, COM_COORD_NUM);

	if (ret >= 0) {
#if defined(CONFIG_SAMSUNG_KERNEL_DEBUG_USER)
		pr_debug("[E-PEN] %x, %x, %x, %x, %x, %x, %x\n",
			 data[0], data[1], data[2], data[3], data[4], data[5],
			 data[6]);
#endif

		if (data[0] & 0x80) {
			/* enable emr device */
			if (!wac_i2c->pen_prox) {

				wac_i2c->pen_prox = 1;

				if (data[0] & 0x40)
					wac_i2c->tool = BTN_TOOL_RUBBER;
				else
					wac_i2c->tool = BTN_TOOL_PEN;
#if defined(CONFIG_SAMSUNG_KERNEL_DEBUG_USER)
				pr_debug("[E-PEN] is in(%d)\n", wac_i2c->tool);
#endif
			}

			prox = !!(data[0] & 0x10);
			stylus = !!(data[0] & 0x20);
			rubber = !!(data[0] & 0x40);
			rdy = !!(data[0] & 0x80);

			x = ((u16) data[1] << 8) + (u16) data[2];
			y = ((u16) data[3] << 8) + (u16) data[4];
			pressure = ((u16) data[5] << 8) + (u16) data[6];

#ifdef WACOM_IMPORT_FW_ALGO
			/* Change Position to Active Area */
			if (x <= origin_offset[0])
				x = 0;
			else
				x = x - origin_offset[0];
			if (y <= origin_offset[1])
				y = 0;
			else
				y = y - origin_offset[1];
#ifdef COOR_WORK_AROUND
			wacom_i2c_coord_offset(&x, &y);
			wacom_i2c_coord_average(&x, &y, rdy);
#endif
#endif

			if (wac_i2c->wac_pdata->x_invert)
				x = wac_i2c->wac_feature->x_max - x;
			if (wac_i2c->wac_pdata->y_invert)
				y = wac_i2c->wac_feature->y_max - y;

			if (wac_i2c->wac_pdata->xy_switch) {
				tmp = x;
				x = y;
				y = tmp;
			}
#ifdef COOR_WORK_AROUND
			/* Add offset */
			x = x + tilt_offsetX[user_hand][screen_rotate];
			y = y + tilt_offsetY[user_hand][screen_rotate];
#endif
			if (wacom_i2c_coord_range(&x, &y)) {
				input_report_abs(wac_i2c->input_dev, ABS_X, x);
				input_report_abs(wac_i2c->input_dev, ABS_Y, y);
				input_report_abs(wac_i2c->input_dev,
						 ABS_PRESSURE, pressure);
				input_report_key(wac_i2c->input_dev,
						 BTN_STYLUS, stylus);
				input_report_key(wac_i2c->input_dev, BTN_TOUCH,
						 prox);
				input_report_key(wac_i2c->input_dev,
						 wac_i2c->tool, 1);
				input_sync(wac_i2c->input_dev);

				if (prox && !wac_i2c->pen_pressed) {
#ifdef SEC_DVFS_LOCK
					set_dvfs_lock(wac_i2c, true);
#endif
#if defined(CONFIG_SAMSUNG_KERNEL_DEBUG_USER)
					printk(KERN_DEBUG
						"[E-PEN] is pressed(%d,%d,%d)(%d)\n",
						x, y, pressure, wac_i2c->tool);
#else
					printk(KERN_DEBUG "[E-PEN] pressed\n");
#endif

				} else if (!prox && wac_i2c->pen_pressed) {
#ifdef SEC_DVFS_LOCK
					set_dvfs_lock(wac_i2c, false);
#endif
#if defined(CONFIG_SAMSUNG_KERNEL_DEBUG_USER)
					printk(KERN_DEBUG
						"[E-PEN] is released(%d,%d,%d)(%d)\n",
						x, y, pressure, wac_i2c->tool);
#else
					printk(KERN_DEBUG "[E-PEN] released\n");
#endif
				}

				wac_i2c->pen_pressed = prox;

#if defined(CONFIG_SAMSUNG_KERNEL_DEBUG_USER)
				if (stylus && !wac_i2c->side_pressed)
					printk(KERN_DEBUG "[E-PEN] side on");
				else if (!stylus && wac_i2c->side_pressed)
					printk(KERN_DEBUG "[E-PEN] side off");
#endif
				wac_i2c->side_pressed = stylus;
			}
#if defined(CONFIG_SAMSUNG_KERNEL_DEBUG_USER)
			else
			   printk("[E-PEN] raw data x=0x%x, y=0x%x\n",
			   x, y);
#endif
		} else {
#ifdef COOR_WORK_AROUND
			/* enable emr device */
			wacom_i2c_coord_average(0, 0, 0);
#endif

			if (wac_i2c->pen_prox) {
				/* input_report_abs(wac->input_dev,
				ABS_X, x); */
				/* input_report_abs(wac->input_dev,
				ABS_Y, y); */
				input_report_abs(wac_i2c->input_dev,
						 ABS_PRESSURE, 0);
				input_report_key(wac_i2c->input_dev,
						 BTN_STYLUS, 0);
				input_report_key(wac_i2c->input_dev, BTN_TOUCH,
						 0);
				input_report_key(wac_i2c->input_dev,
						 wac_i2c->tool, 0);
				input_sync(wac_i2c->input_dev);

#if defined(CONFIG_SAMSUNG_KERNEL_DEBUG_USER)
				if (wac_i2c->pen_pressed
					|| wac_i2c->side_pressed)
					printk(KERN_DEBUG "[E-PEN] is out");
				else
					printk(KERN_DEBUG "[E-PEN] is out");
#endif
			}
			wac_i2c->pen_prox = 0;
			wac_i2c->pen_pressed = 0;
			wac_i2c->side_pressed = 0;

#ifdef SEC_DVFS_LOCK
			set_dvfs_lock(wac_i2c, false);
#endif
		}
	} else {
		printk(KERN_ERR "[E-PEN]: failed to read i2c\n");
		return -1;
	}

	return 0;
}
コード例 #7
0
static void s3c_keypad_timer_handler(unsigned long data)
{
	u32 press_mask;
	u32 release_mask;
	u32 restart_timer = 0;
	int i,col;
	struct s3c_keypad *pdata = (struct s3c_keypad *)data;
	struct input_dev *dev = pdata->dev;
	struct timer_list * timer = &pdata->keypad_timer;
#if defined(CONFIG_MACH_CHIEF) && !defined(CONFIG_TIKAL_MPCS) && !defined(CONFIG_MACH_TREBON)
	int skipcol=0;
#endif

	keypad_scan();


    for(col=0; col < KEYPAD_COLUMNS; col++) {
		press_mask = ((keymask[col] ^ prevmask[col]) & keymask[col]); 
		release_mask = ((keymask[col] ^ prevmask[col]) & prevmask[col]); 

#ifdef CONFIG_CPU_FREQ
#if USE_PERF_LEVEL_KEYPAD
//		if (press_mask || release_mask)
//			set_dvfs_target_level(LEV_400MHZ);
#endif
#endif
		i = col * KEYPAD_ROWS;

		while (press_mask) {
			if (press_mask & 1) {
#if defined(CONFIG_MACH_CHIEF) && !defined(CONFIG_TIKAL_MPCS) && !defined(CONFIG_MACH_TREBON)
				/* 
				 *  when camera & focus key press is detected simultaneously,
				 *  report focus first and camera second, so that platform
				 *  detects camera key repeat event (for key long press)
				 */
				if ( col==2 && ((keymask[3] ^ prevmask[3]) & keymask[3])) {
					input_report_key(dev,pdata->keycodes[3],1);
#ifdef DEBUG_LOG_ENABLE
					printk(KERN_DEBUG"[KEYPAD] key Pressed  : key %d map %d\n",3, pdata->keycodes[3]);
#else
					printk(KERN_DEBUG"[KEYPAD] key Pressed\n");
#endif
					skipcol = 1;
				}
#endif
				input_report_key(dev,pdata->keycodes[i],1);
#if defined(CONFIG_MACH_CHIEF) && !defined(CONFIG_TIKAL_MPCS) && !defined(CONFIG_MACH_TREBON)
                keyled_timer_start(); /* keypad_led */
#endif				
/* #ifdef CONFIG_KERNEL_DEBUG_SEC */
#ifdef DEBUG_LOG_ENABLE
				printk(KERN_DEBUG"[KEYPAD] key Pressed  : key %d map %d\n",i, pdata->keycodes[i]);
#else
				printk(KERN_DEBUG"[KEYPAD] key Pressed\n");
#endif
						}
			press_mask >>= 1;
			i++;
#if defined(CONFIG_MACH_CHIEF) && !defined(CONFIG_TIKAL_MPCS) && !defined(CONFIG_MACH_TREBON)
			if (skipcol) {
				press_mask >>= 1;
				i++;
			}
#endif
		}

		i = col * KEYPAD_ROWS;

		while (release_mask) {
			if (release_mask & 1) {
				input_report_key(dev,pdata->keycodes[i],0);
#if defined(CONFIG_MACH_CHIEF) && !defined(CONFIG_TIKAL_MPCS) && !defined(CONFIG_MACH_TREBON)
		   keyled_timer_start(); /* keypad_led */
#endif				
/* #ifdef CONFIG_KERNEL_DEBUG_SEC */
#ifdef DEBUG_LOG_ENABLE
				printk(KERN_DEBUG"[KEYPAD] key Released : %d  map %d\n",i,pdata->keycodes[i]);
#else
				printk(KERN_DEBUG"[KEYPAD] key Released\n");
#endif

            }
			release_mask >>= 1;
			i++;
		}
		prevmask[col] = keymask[col];

		restart_timer |= keymask[col];

#if defined(CONFIG_MACH_CHIEF) && !defined(CONFIG_TIKAL_MPCS) && !defined(CONFIG_MACH_TREBON)
		/* skip next column, we've already proccessed this*/
		if (skipcol) {
			col++;
			skipcol = 0;
		}
#endif
	}
	
	if (restart_timer) {
#if defined(CONFIG_MACH_CHIEF)
		 mod_timer(timer,jiffies + (5*HZ/100));
#else
		mod_timer(timer, timer->expires);
#endif
	} else {
		writel(KEYIFCON_INIT, key_base+S3C_KEYIFCON);
		pdata->keypad_timer_on = FALSE;
	}

}
コード例 #8
0
static irqreturn_t touchkey_interrupt_thread(int irq, void *touchkey_devdata)
{
	u8 data;
	int i;
	int ret;
	int scancode;
	struct cypress_touchkey_devdata *devdata = touchkey_devdata;

	ret = i2c_touchkey_read_byte(devdata, &data);
	if (ret || (data & ESD_STATE_MASK)) {
		ret = recovery_routine(devdata);
		if (ret) {
			dev_err(&devdata->client->dev, "%s: touchkey recovery "
					"failed!\n", __func__);
			goto err;
		}
	}
    if (devdata->has_legacy_keycode) {
		scancode = (data & SCANCODE_MASK) - 1;
		if (scancode < 0 || scancode >= devdata->pdata->keycode_cnt) {
			dev_err(&devdata->client->dev, "%s: scancode is out of "
                    "range\n", __func__);
			goto err;
		}
        
#ifdef CONFIG_TOUCH_WAKE
		if (!device_is_suspended())
#endif
        {
			input_report_key(devdata->input_dev,
                             devdata->pdata->keycode[scancode],
                             !(data & UPDOWN_EVENT_MASK));
        }
#if defined(CONFIG_TOUCH_WAKE) || defined(CONFIG_BLD)
		if (!(data & UPDOWN_EVENT_MASK))
        {
#ifdef CONFIG_BLD			
			touchkey_pressed();
#endif
#ifdef CONFIG_TOUCH_WAKE
			touch_press();
#endif
        }
#endif
	} else {
#ifdef CONFIG_TOUCH_WAKE
		if (!device_is_suspended())
#endif
        {
			for (i = 0; i < devdata->pdata->keycode_cnt; i++)
			    input_report_key(devdata->input_dev,
                                 devdata->pdata->keycode[i],
                                 !!(data & (1U << i)));
        }
        
#if defined(CONFIG_TOUCH_WAKE) || defined(CONFIG_BLD)
		for (i = 0; i < devdata->pdata->keycode_cnt; i++)
        {
			if(!!(data & (1U << i)))
            {
#ifdef CONFIG_BLD			
				touchkey_pressed();
#endif
#ifdef CONFIG_TOUCH_WAKE
				touch_press();
#endif
				break;
            }
        }
#endif
	}
    
	input_sync(devdata->input_dev);
err:
	return IRQ_HANDLED;
}
コード例 #9
0
static irqreturn_t touchkey_interrupt(int irq, void *dev_id)
{
	struct touchkey_i2c *tkey_i2c = dev_id;
	u8 data[3];
	int ret;
	int retry = 10;
	int keycode_type = 0;
	int pressed;

	set_touchkey_debug('a');

	retry = 3;
	while (retry--) {
		ret = i2c_touchkey_read(tkey_i2c->client, KEYCODE_REG, data, 3);
		if (!ret) {
			keycode_type = (data[0] & TK_BIT_KEYCODE);
			if (keycode_type <= 0
				|| keycode_type >= touchkey_count) {
				printk(KERN_DEBUG "[Touchkey] keycode_type err"
					" ret:%d, retry: %d\n",
					keycode_type, retry);
				continue;
			}
			break;
		}
		else {
			printk(KERN_DEBUG
			       "[TouchKey] i2c read failed, ret:%d, retry: %d\n",
			       ret, retry);
			continue;
		}
	}
	if (ret < 0)
		return IRQ_HANDLED;

	set_touchkey_debug(data[0]);

	keycode_type = (data[0] & TK_BIT_KEYCODE);
	pressed = !(data[0] & TK_BIT_PRESS_EV);

	if (keycode_type <= 0 || keycode_type >= touchkey_count) {
		int i;
		printk(KERN_DEBUG "[Touchkey] keycode_type err %d."
			" Release all keys\n", keycode_type);
		/* release keys */
		for (i = 1; i < touchkey_count; ++i) {
			input_report_key(tkey_i2c->input_dev,
				touchkey_keycode[i], 0);
		}
		input_sync(tkey_i2c->input_dev);
		return IRQ_HANDLED;
	}

	if (pressed)
		set_touchkey_debug('P');

	if (get_tsp_status() && pressed)
		printk(KERN_DEBUG "[TouchKey] touch is pressed. Pass touchkey event\n");
	else {
		input_report_key(tkey_i2c->input_dev,
				 touchkey_keycode[keycode_type], pressed);
		input_sync(tkey_i2c->input_dev);
#if !defined(CONFIG_SAMSUNG_PRODUCT_SHIP)
		printk(KERN_DEBUG "[TouchKey] keycode:%d pressed:%d\n",
		   touchkey_keycode[keycode_type], pressed);
#else
		printk(KERN_DEBUG "[TouchKey] pressed:%d\n",
			pressed);
#endif

		#if defined(CONFIG_TARGET_LOCALE_KOR)
		if (g_debug_tkey == true) {
			printk(KERN_DEBUG "[TouchKey] keycode[%d]=%d pressed:%d\n",
			keycode_type, touchkey_keycode[keycode_type], pressed);
		} else {
			printk(KERN_DEBUG "[TouchKey] pressed:%d\n", pressed);
		}
		#endif
	}
	set_touchkey_debug('A');
	return IRQ_HANDLED;
}
コード例 #10
0
static int hkey_poll_kthread(void *data)
{
	unsigned long t = 0;
	int offset, level;
	unsigned int keycode;
	u8 scancode;

	mutex_lock(&hkey_poll_mutex);

	offset = hkey_ec_get_offset();
	if (offset < 0) {
		vdbg_printk(LENSL_WARNING,
			"Failed to read hotkey register offset from EC\n");
		hkey_ec_prev_offset = 0;
	} else
		hkey_ec_prev_offset = offset;

	while (!kthread_should_stop() && hkey_poll_hz) {
		if (t == 0)
			t = 1000/hkey_poll_hz;
		t = msleep_interruptible(t);
		if (unlikely(kthread_should_stop()))
			break;
		try_to_freeze();
		if (t > 0)
			continue;
		offset = hkey_ec_get_offset();
		if (offset < 0) {
			vdbg_printk(LENSL_WARNING,
			   "Failed to read hotkey register offset from EC\n");
			continue;
		}
		if (offset == hkey_ec_prev_offset)
			continue;

		if (ec_read(0x0A + offset, &scancode)) {
			vdbg_printk(LENSL_WARNING,
				"Failed to read hotkey code from EC\n");
			continue;
		}
		keycode = ec_scancode_to_keycode(scancode);
		vdbg_printk(LENSL_DEBUG,
		   "Got hotkey keycode %d (scancode %d)\n", keycode, scancode);

		/* Special handling for brightness keys. We do it here and not
		   via an ACPI notifier in order to prevent possible conflicts
		   with video.c */
		if (keycode == KEY_BRIGHTNESSDOWN) {
			if (control_backlight && backlight) {
				level = lensl_bd_get_brightness(backlight);
				if (0 <= --level)
					lensl_bd_set_brightness_int(level);
			} else
				keycode = KEY_RESERVED;
		} else if (keycode == KEY_BRIGHTNESSUP) {
			if (control_backlight && backlight) {
				level = lensl_bd_get_brightness(backlight);
				if (backlight_levels.count > ++level)
					lensl_bd_set_brightness_int(level);
			} else
				keycode = KEY_RESERVED;
		}

		if (keycode != KEY_RESERVED) {
			input_report_key(hkey_inputdev, keycode, 1);
			input_sync(hkey_inputdev);
			input_report_key(hkey_inputdev, keycode, 0);
			input_sync(hkey_inputdev);
		}
		hkey_ec_prev_offset = offset;
	}

	mutex_unlock(&hkey_poll_mutex);
	return 0;
}
コード例 #11
0
static void s3c_keypad_timer_handler(unsigned long data)
{
	u32 press_mask;
	u32 release_mask;
	u32 restart_timer = 0;
	int i,col;
	struct s3c_keypad *pdata = (struct s3c_keypad *)data;
	struct input_dev *dev = pdata->dev;
	struct timer_list * timer = &pdata->keypad_timer;

	keypad_scan();


	for(col=0; col < KEYPAD_COLUMNS; col++) {
		press_mask = ((keymask[col] ^ prevmask[col]) & keymask[col]); 
		release_mask = ((keymask[col] ^ prevmask[col]) & prevmask[col]); 

#ifdef CONFIG_CPU_FREQ
#if USE_PERF_LEVEL_KEYPAD
//		if (press_mask || release_mask)
//			set_dvfs_target_level(LEV_400MHZ);
#endif
#endif
		i = col * KEYPAD_ROWS;

		while (press_mask) {
			if (press_mask & 1) {
				input_report_key(dev,pdata->keycodes[i],1);
#ifdef CONFIG_MACH_CHIEF				
                keyled_timer_start(); /* keypad_led */
#endif				
/* #ifdef CONFIG_KERNEL_DEBUG_SEC */
#ifdef DEBUG_LOG_ENABLE
				printk(KERN_DEBUG"[KEYPAD] key Pressed  : key %d map %d\n",i, pdata->keycodes[i]);
#else
				printk(KERN_DEBUG"[KEYPAD] key Pressed\n");
#endif
						}
			press_mask >>= 1;
			i++;
		}

		i = col * KEYPAD_ROWS;

		while (release_mask) {
			if (release_mask & 1) {
				input_report_key(dev,pdata->keycodes[i],0);
#ifdef CONFIG_MACH_CHIEF				
                keyled_timer_start(); /* keypad_led */
#endif				
/* #ifdef CONFIG_KERNEL_DEBUG_SEC */
#ifdef DEBUG_LOG_ENABLE
				printk(KERN_DEBUG"[KEYPAD] key Released : %d  map %d\n",i,pdata->keycodes[i]);
#else
				printk(KERN_DEBUG"[KEYPAD] key Released\n");
#endif

            }
			release_mask >>= 1;
			i++;
		}
		prevmask[col] = keymask[col];

		restart_timer |= keymask[col];
	}


	if (restart_timer) {
		mod_timer(timer, timer->expires);
	} else {
		writel(KEYIFCON_INIT, key_base+S3C_KEYIFCON);
		pdata->keypad_timer_on = FALSE;
	}

}
コード例 #12
0
ファイル: wacom_sys.c プロジェクト: daveti/prov-kernel
void wacom_report_key(void *wcombo, unsigned int key_type, int key_data)
{
	input_report_key(get_input_dev((struct wacom_combo *)wcombo), key_type, key_data);
}
コード例 #13
0
ファイル: sc_keypad.c プロジェクト: ShinySide/SM-G361H
static irqreturn_t sci_keypad_isr(int irq, void *dev_id)
{
	unsigned short key = 0;
	unsigned long value;
	struct sci_keypad_t *sci_kpd = dev_id;
	unsigned long int_status = __raw_readl(KPD_INT_MASK_STATUS);
	unsigned long key_status = __raw_readl(KPD_KEY_STATUS);
	unsigned short *keycodes = sci_kpd->input_dev->keycode;
	unsigned int row_shift = get_count_order(sci_kpd->cols);
	int col, row;


	value = __raw_readl(KPD_INT_CLR);
	value |= KPD_INT_ALL;
	__raw_writel(value, KPD_INT_CLR);
	if ((int_status & KPD_PRESS_INT0)) {
		col = KPD_INT0_COL(key_status);
		row = KPD_INT0_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03dD\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 1);
		input_sync(sci_kpd->input_dev);
	}
	if (int_status & KPD_RELEASE_INT0) {
		col = KPD_INT0_COL(key_status);
		row = KPD_INT0_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03dU\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 0);
		input_sync(sci_kpd->input_dev);
	}

	if ((int_status & KPD_PRESS_INT1)) {
		col = KPD_INT1_COL(key_status);
		row = KPD_INT1_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03dD\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 1);
		input_sync(sci_kpd->input_dev);
	}
	if (int_status & KPD_RELEASE_INT1) {
		col = KPD_INT1_COL(key_status);
		row = KPD_INT1_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03dU\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 0);
		input_sync(sci_kpd->input_dev);
	}

	if ((int_status & KPD_PRESS_INT2)) {
		col = KPD_INT2_COL(key_status);
		row = KPD_INT2_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03d\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 1);
		input_sync(sci_kpd->input_dev);
	}
	if (int_status & KPD_RELEASE_INT2) {
		col = KPD_INT2_COL(key_status);
		row = KPD_INT2_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03d\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 0);
		input_sync(sci_kpd->input_dev);
	}

	if (int_status & KPD_PRESS_INT3) {
		col = KPD_INT3_COL(key_status);
		row = KPD_INT3_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03d\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 1);
		input_sync(sci_kpd->input_dev);
	}
	if (int_status & KPD_RELEASE_INT3) {
		col = KPD_INT3_COL(key_status);
		row = KPD_INT3_ROW(key_status);
		key = keycodes[MATRIX_SCAN_CODE(row, col, row_shift)];

#if PRINT_KEY_LOG
		printk("%03d\n", key);
#endif
		input_report_key(sci_kpd->input_dev, key, 0);
		input_sync(sci_kpd->input_dev);
	}

	return IRQ_HANDLED;
}
コード例 #14
0
ファイル: hil_kbd.c プロジェクト: 03199618/linux
static void hil_dev_handle_ptr_events(struct hil_dev *ptr)
{
	struct input_dev *dev = ptr->dev;
	int idx = ptr->idx4 / 4;
	hil_packet p = ptr->data[idx - 1];
	int i, cnt, laxis;
	bool absdev, ax16;

	if ((p & HIL_CMDCT_POL) != idx - 1) {
		printk(KERN_WARNING PREFIX
			"Malformed poll packet %x (idx = %i)\n", p, idx);
		return;
	}

	i = (p & HIL_POL_AXIS_ALT) ? 3 : 0;
	laxis = (p & HIL_POL_NUM_AXES_MASK) + i;

	ax16 = ptr->idd[1] & HIL_IDD_HEADER_16BIT; /* 8 or 16bit resolution */
	absdev = ptr->idd[1] & HIL_IDD_HEADER_ABS;

	for (cnt = 1; i < laxis; i++) {
		unsigned int lo, hi, val;

		lo = ptr->data[cnt++] & HIL_PKT_DATA_MASK;
		hi = ax16 ? (ptr->data[cnt++] & HIL_PKT_DATA_MASK) : 0;

		if (absdev) {
			val = lo + (hi << 8);
#ifdef TABLET_AUTOADJUST
			if (val < input_abs_get_min(dev, ABS_X + i))
				input_abs_set_min(dev, ABS_X + i, val);
			if (val > input_abs_get_max(dev, ABS_X + i))
				input_abs_set_max(dev, ABS_X + i, val);
#endif
			if (i % 3)
				val = input_abs_get_max(dev, ABS_X + i) - val;
			input_report_abs(dev, ABS_X + i, val);
		} else {
			val = (int) (((int8_t) lo) | ((int8_t) hi << 8));
			if (i % 3)
				val *= -1;
			input_report_rel(dev, REL_X + i, val);
		}
	}

	while (cnt < idx - 1) {
		unsigned int btn = ptr->data[cnt++];
		int up = btn & 1;

		btn &= 0xfe;
		if (btn == 0x8e)
			continue; /* TODO: proximity == touch? */
		if (btn > 0x8c || btn < 0x80)
			continue;
		btn = (btn - 0x80) >> 1;
		btn = ptr->btnmap[btn];
		input_report_key(dev, btn, !up);
	}

	input_sync(dev);
}
コード例 #15
0
ファイル: ig_input.c プロジェクト: CSU-GH/okl4_3.0
static irqreturn_t 
ig_input_interrupt(int irq, void *dev_id)
{
	struct stream_packet *packet;
	uintptr_t next;
	int i;
	int data = 0;
	int kick = 0;

//	packet = ig_input->rx_complete;
        packet = memsect_to_vaddr(ig_input, ig_input->control->rx);	
	while(packet) {
		int new_q = 0;
		uint16_t *keys;
		next = packet->next;
		if ((packet->status & COMPLETED) == 0) {
			break;
		}
		packet->status = 0;
                ig_input->control->rx = next;


		/* Append to free list */
		data = 1;
		keys = (uint16_t*)packet->data;
		for (i=0; i < (packet->xferred/2); i++) {
			if (keys[i] & 0x4000) {
				//printk("Mouse %x, %d\n", keys[i] & 0xff, (keys[i] & 0x100) ? -1 : 1);
				if (keys[i] & 0x8000) {
					input_report_rel(ig_input->input_dev, keys[i] & 0x0ff,
							(keys[i] & 0x100) ? -1 : 1);
				}
			} else {
				//printk("Key %s: %x\n", (keys[i] & 0x8000) ? "down" : "up", keys[i] & 0x01ff);
				input_report_key(ig_input->input_dev, keys[i] & 0x01ff, ((keys[i] & 0x8000) != 0));
			}
		}
		
		packet->next = ~0;
		packet->size = PACKET_SIZE;
		packet->xferred = 0;
		
		if (ig_input->rx_last != NULL) {
			ig_input->rx_last->next = vaddr_to_memsect(ig_input, packet);
			if (ig_input->rx_last->status & TERMINATED) {
				new_q = 1;
			}
		} else {
			new_q = 1;
		}
		if (new_q) {
			ig_input->control->rx = vaddr_to_memsect(ig_input, packet);
			kick = 1;
		}
		ig_input->rx_last = packet;

		if (next == ~0) {
			packet = NULL;
		} else {
			packet = memsect_to_vaddr(ig_input, next);
		}
	}

	if (data) {
		input_sync(ig_input->input_dev);
	}

	if (kick) {
		L4_Notify(ig_input->server, 0x1);
	}

    return IRQ_HANDLED;
}
コード例 #16
0
static void tps6507x_ts_handler(struct work_struct *work)
{
	struct tps6507x_ts *tsc =  container_of(work,
				struct tps6507x_ts, work.work);
	struct input_dev *input_dev = tsc->input_dev;
	int pendown;
	int schd;
	int poll = 0;
	s32 ret;

	ret =  tps6507x_adc_conversion(tsc, TPS6507X_TSCMODE_PRESSURE,
				       &tsc->tc.pressure);
	if (ret)
		goto done;

	pendown = tsc->tc.pressure > tsc->min_pressure;

	if (unlikely(!pendown && tsc->pendown)) {
		dev_dbg(tsc->dev, "UP\n");
		input_report_key(input_dev, BTN_TOUCH, 0);
		input_report_abs(input_dev, ABS_PRESSURE, 0);
		input_sync(input_dev);
		tsc->pendown = 0;
	}

	if (pendown) {

		if (!tsc->pendown) {
			dev_dbg(tsc->dev, "DOWN\n");
			input_report_key(input_dev, BTN_TOUCH, 1);
		} else
			dev_dbg(tsc->dev, "still down\n");

		ret =  tps6507x_adc_conversion(tsc, TPS6507X_TSCMODE_X_POSITION,
					       &tsc->tc.x);
		if (ret)
			goto done;

		ret =  tps6507x_adc_conversion(tsc, TPS6507X_TSCMODE_Y_POSITION,
					       &tsc->tc.y);
		if (ret)
			goto done;

		input_report_abs(input_dev, ABS_X, tsc->tc.x);
		input_report_abs(input_dev, ABS_Y, tsc->tc.y);
		input_report_abs(input_dev, ABS_PRESSURE, tsc->tc.pressure);
		input_sync(input_dev);
		tsc->pendown = 1;
		poll = 1;
	}

done:
	/* always poll if not using interrupts */
	poll = 1;

	if (poll) {
		schd = schedule_delayed_work(&tsc->work,
					msecs_to_jiffies(tsc->poll_period));
		if (schd)
			tsc->polling = 1;
		else {
			tsc->polling = 0;
			dev_err(tsc->dev, "re-schedule failed");
		}
	} else
		tsc->polling = 0;

	ret = tps6507x_adc_standby(tsc);
}
コード例 #17
0
ファイル: kpd.c プロジェクト: linzhangru/Sony-xa-kernel-tuba
long kpd_dev_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
{
	/* void __user *uarg = (void __user *)arg; */

	switch (cmd) {
#if KPD_AUTOTEST
	case PRESS_OK_KEY:	/* KPD_AUTOTEST disable auto test setting to resolve CR ALPS00464496 */
		if (test_bit(KEY_OK, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS OK KEY!!\n");
			input_report_key(kpd_input_dev, KEY_OK, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support OK KEY!!\n");
		}
		break;
	case RELEASE_OK_KEY:
		if (test_bit(KEY_OK, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE OK KEY!!\n");
			input_report_key(kpd_input_dev, KEY_OK, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support OK KEY!!\n");
		}
		break;
	case PRESS_MENU_KEY:
		if (test_bit(KEY_MENU, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS MENU KEY!!\n");
			input_report_key(kpd_input_dev, KEY_MENU, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support MENU KEY!!\n");
		}
		break;
	case RELEASE_MENU_KEY:
		if (test_bit(KEY_MENU, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE MENU KEY!!\n");
			input_report_key(kpd_input_dev, KEY_MENU, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support MENU KEY!!\n");
		}

		break;
	case PRESS_UP_KEY:
		if (test_bit(KEY_UP, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS UP KEY!!\n");
			input_report_key(kpd_input_dev, KEY_UP, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support UP KEY!!\n");
		}
		break;
	case RELEASE_UP_KEY:
		if (test_bit(KEY_UP, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE UP KEY!!\n");
			input_report_key(kpd_input_dev, KEY_UP, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support UP KEY!!\n");
		}
		break;
	case PRESS_DOWN_KEY:
		if (test_bit(KEY_DOWN, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS DOWN KEY!!\n");
			input_report_key(kpd_input_dev, KEY_DOWN, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support DOWN KEY!!\n");
		}
		break;
	case RELEASE_DOWN_KEY:
		if (test_bit(KEY_DOWN, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE DOWN KEY!!\n");
			input_report_key(kpd_input_dev, KEY_DOWN, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support DOWN KEY!!\n");
		}
		break;
	case PRESS_LEFT_KEY:
		if (test_bit(KEY_LEFT, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS LEFT KEY!!\n");
			input_report_key(kpd_input_dev, KEY_LEFT, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support LEFT KEY!!\n");
		}
		break;
	case RELEASE_LEFT_KEY:
		if (test_bit(KEY_LEFT, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE LEFT KEY!!\n");
			input_report_key(kpd_input_dev, KEY_LEFT, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support LEFT KEY!!\n");
		}
		break;

	case PRESS_RIGHT_KEY:
		if (test_bit(KEY_RIGHT, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS RIGHT KEY!!\n");
			input_report_key(kpd_input_dev, KEY_RIGHT, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support RIGHT KEY!!\n");
		}
		break;
	case RELEASE_RIGHT_KEY:
		if (test_bit(KEY_RIGHT, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE RIGHT KEY!!\n");
			input_report_key(kpd_input_dev, KEY_RIGHT, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support RIGHT KEY!!\n");
		}
		break;
	case PRESS_HOME_KEY:
		if (test_bit(KEY_HOME, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS HOME KEY!!\n");
			input_report_key(kpd_input_dev, KEY_HOME, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support HOME KEY!!\n");
		}
		break;
	case RELEASE_HOME_KEY:
		if (test_bit(KEY_HOME, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE HOME KEY!!\n");
			input_report_key(kpd_input_dev, KEY_HOME, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support HOME KEY!!\n");
		}
		break;
	case PRESS_BACK_KEY:
		if (test_bit(KEY_BACK, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS BACK KEY!!\n");
			input_report_key(kpd_input_dev, KEY_BACK, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support BACK KEY!!\n");
		}
		break;
	case RELEASE_BACK_KEY:
		if (test_bit(KEY_BACK, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE BACK KEY!!\n");
			input_report_key(kpd_input_dev, KEY_BACK, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support BACK KEY!!\n");
		}
		break;
	case PRESS_CALL_KEY:
		if (test_bit(KEY_CALL, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS CALL KEY!!\n");
			input_report_key(kpd_input_dev, KEY_CALL, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support CALL KEY!!\n");
		}
		break;
	case RELEASE_CALL_KEY:
		if (test_bit(KEY_CALL, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE CALL KEY!!\n");
			input_report_key(kpd_input_dev, KEY_CALL, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support CALL KEY!!\n");
		}
		break;

	case PRESS_ENDCALL_KEY:
		if (test_bit(KEY_ENDCALL, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS ENDCALL KEY!!\n");
			input_report_key(kpd_input_dev, KEY_ENDCALL, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support ENDCALL KEY!!\n");
		}
		break;
	case RELEASE_ENDCALL_KEY:
		if (test_bit(KEY_ENDCALL, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE ENDCALL KEY!!\n");
			input_report_key(kpd_input_dev, KEY_ENDCALL, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support ENDCALL KEY!!\n");
		}
		break;
	case PRESS_VLUP_KEY:
		if (test_bit(KEY_VOLUMEUP, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS VOLUMEUP KEY!!\n");
			input_report_key(kpd_input_dev, KEY_VOLUMEUP, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support VOLUMEUP KEY!!\n");
		}
		break;
	case RELEASE_VLUP_KEY:
		if (test_bit(KEY_VOLUMEUP, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE VOLUMEUP KEY!!\n");
			input_report_key(kpd_input_dev, KEY_VOLUMEUP, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support VOLUMEUP KEY!!\n");
		}
		break;
	case PRESS_VLDOWN_KEY:
		if (test_bit(KEY_VOLUMEDOWN, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS VOLUMEDOWN KEY!!\n");
			input_report_key(kpd_input_dev, KEY_VOLUMEDOWN, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support VOLUMEDOWN KEY!!\n");
		}
		break;
	case RELEASE_VLDOWN_KEY:
		if (test_bit(KEY_VOLUMEDOWN, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE VOLUMEDOWN KEY!!\n");
			input_report_key(kpd_input_dev, KEY_VOLUMEDOWN, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support VOLUMEDOWN KEY!!\n");
		}
		break;
	case PRESS_FOCUS_KEY:
		if (test_bit(KEY_FOCUS, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS FOCUS KEY!!\n");
			input_report_key(kpd_input_dev, KEY_FOCUS, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support FOCUS KEY!!\n");
		}
		break;
	case RELEASE_FOCUS_KEY:
		if (test_bit(KEY_FOCUS, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE FOCUS KEY!!\n");
			input_report_key(kpd_input_dev, KEY_FOCUS, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support RELEASE KEY!!\n");
		}
		break;
	case PRESS_CAMERA_KEY:
		if (test_bit(KEY_CAMERA, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS CAMERA KEY!!\n");
			input_report_key(kpd_input_dev, KEY_CAMERA, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support CAMERA KEY!!\n");
		}
		break;
	case RELEASE_CAMERA_KEY:
		if (test_bit(KEY_CAMERA, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE CAMERA KEY!!\n");
			input_report_key(kpd_input_dev, KEY_CAMERA, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support CAMERA KEY!!\n");
		}
		break;
	case PRESS_POWER_KEY:
		if (test_bit(KEY_POWER, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] PRESS POWER KEY!!\n");
			input_report_key(kpd_input_dev, KEY_POWER, 1);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support POWER KEY!!\n");
		}
		break;
	case RELEASE_POWER_KEY:
		if (test_bit(KEY_POWER, kpd_input_dev->keybit)) {
			kpd_print("[AUTOTEST] RELEASE POWER KEY!!\n");
			input_report_key(kpd_input_dev, KEY_POWER, 0);
			input_sync(kpd_input_dev);
		} else {
			kpd_print("[AUTOTEST] Not Support POWER KEY!!\n");
		}
		break;
#endif

	case SET_KPD_KCOL:
		kpd_auto_test_for_factorymode();	/* API 3 for kpd factory mode auto-test */
		kpd_print("[kpd_auto_test_for_factorymode] test performed!!\n");
		break;
	default:
		return -EINVAL;
	}

	return 0;
}
コード例 #18
0
static int __devinit pmic8xxx_pwrkey_probe(struct platform_device *pdev)
{
    struct input_dev *pwr;
    int key_release_irq = platform_get_irq(pdev, 0);
    int key_press_irq = platform_get_irq(pdev, 1);
    int err;
    unsigned int delay;
    u8 pon_cntl;
    struct pmic8xxx_pwrkey *pwrkey;
    const struct pm8xxx_pwrkey_platform_data *pdata =
        dev_get_platdata(&pdev->dev);

    if (!pdata) {
        dev_err(&pdev->dev, "power key platform data not supplied\n");
        return -EINVAL;
    }

    /* Valid range of pwr key trigger delay is 1/64 sec to 2 seconds. */
    if (pdata->kpd_trigger_delay_us > USEC_PER_SEC * 2 ||
            pdata->kpd_trigger_delay_us < USEC_PER_SEC / 64) {
        dev_err(&pdev->dev, "invalid power key trigger delay\n");
        return -EINVAL;
    }

    pwrkey = kzalloc(sizeof(*pwrkey), GFP_KERNEL);
    if (!pwrkey)
        return -ENOMEM;

    pwrkey->pdata = pdata;

    pwr = input_allocate_device();
    if (!pwr) {
        dev_dbg(&pdev->dev, "Can't allocate power button\n");
        err = -ENOMEM;
        goto free_pwrkey;
    }

    input_set_capability(pwr, EV_KEY, KEY_POWER);

    pwr->name = "pmic8xxx_pwrkey";
    pwr->phys = "pmic8xxx_pwrkey/input0";
    pwr->dev.parent = &pdev->dev;

    delay = (pdata->kpd_trigger_delay_us << 6) / USEC_PER_SEC;
    delay = ilog2(delay);

    err = pm8xxx_readb(pdev->dev.parent, PON_CNTL_1, &pon_cntl);
    if (err < 0) {
        dev_err(&pdev->dev, "failed reading PON_CNTL_1 err=%d\n", err);
        goto free_input_dev;
    }

    pon_cntl &= ~PON_CNTL_TRIG_DELAY_MASK;
    pon_cntl |= (delay & PON_CNTL_TRIG_DELAY_MASK);
    if (pdata->pull_up)
        pon_cntl |= PON_CNTL_PULL_UP;
    else
        pon_cntl &= ~PON_CNTL_PULL_UP;

    err = pm8xxx_writeb(pdev->dev.parent, PON_CNTL_1, pon_cntl);
    if (err < 0) {
        dev_err(&pdev->dev, "failed writing PON_CNTL_1 err=%d\n", err);
        goto free_input_dev;
    }

    err = input_register_device(pwr);
    if (err) {
        dev_dbg(&pdev->dev, "Can't register power key: %d\n", err);
        goto free_input_dev;
    }

    //zte jiangfeng add
    init_timer(&pwrkey->timer);
    pwrkey->timer.data = (unsigned long)pwrkey;
    pwrkey->timer.function = pwrkey_timer;
    //zte jiangfeng added

    pwrkey->key_press_irq = key_press_irq;
    pwrkey->key_release_irq = key_release_irq;
    pwrkey->pwr = pwr;

    INIT_WORK(&pwrkey->pwrkey_poweroff_work, pwrkey_poweroff);

    platform_set_drvdata(pdev, pwrkey);

    /* check power key status during boot */
    err = pm8xxx_read_irq_stat(pdev->dev.parent, key_press_irq);
    if (err < 0) {
        dev_err(&pdev->dev, "reading irq status failed\n");
        goto unreg_input_dev;
    }
    pwrkey->press = !!err;

    if (pwrkey->press) {
        input_report_key(pwrkey->pwr, KEY_POWER, 1);
        input_sync(pwrkey->pwr);
    }

    err = request_any_context_irq(key_press_irq, pwrkey_press_irq,
                                  IRQF_TRIGGER_RISING, "pmic8xxx_pwrkey_press", pwrkey);
    if (err < 0) {
        dev_dbg(&pdev->dev, "Can't get %d IRQ for pwrkey: %d\n",
                key_press_irq, err);
        goto unreg_input_dev;
    }

    err = request_any_context_irq(key_release_irq, pwrkey_release_irq,
                                  IRQF_TRIGGER_RISING, "pmic8xxx_pwrkey_release", pwrkey);
    if (err < 0) {
        dev_dbg(&pdev->dev, "Can't get %d IRQ for pwrkey: %d\n",
                key_release_irq, err);

        goto free_press_irq;
    }

    device_init_wakeup(&pdev->dev, pdata->wakeup);



    return 0;

free_press_irq:
    free_irq(key_press_irq, NULL);
unreg_input_dev:
    platform_set_drvdata(pdev, NULL);
    input_unregister_device(pwr);
    pwr = NULL;
free_input_dev:
    input_free_device(pwr);
free_pwrkey:
    kfree(pwrkey);
    return err;
}
コード例 #19
0
static irqreturn_t hisi_powerkey_handler(int irq, void *data)
{
	struct hisi_powerkey_info *info = (struct hisi_powerkey_info *)data;

	wake_lock_timeout(&info->pwr_wake_lock, HZ);

	if (info->irq[0] == irq) {
			pr_info("[%s]response press interrupt!\n", __FUNCTION__);
			power_key_ps=true;

#if defined (CONFIG_HUAWEI_DSM)
			powerkey_press_count++;
                    if ((jiffies - powerkey_last_press_time) < msecs_to_jiffies(PRESS_KEY_INTERVAL)) {
                        if (!dsm_client_ocuppy(power_key_dclient)) {
                            dsm_client_record(power_key_dclient, "power key trigger on the abnormal style.\n");
                            dsm_client_notify(power_key_dclient, DSM_POWER_KEY_ERROR_NO);
                        }
                    }
                     powerkey_last_press_time = jiffies;
#endif
                    /* modify by songliangliang for dmd_log> */
			#if defined (CONFIG_FB_HI6220_CLCD)
			lcd_dcm_pwr_add_timer();
			#endif
			input_report_key(info->idev, KEY_POWER, POWER_KEY_PRESS);
			input_sync(info->idev);
	} else if (info->irq[1] == irq) {
			pr_info("[%s]response release interrupt!\n", __FUNCTION__);
			#if defined(CONFIG_HISILICON_PLATFORM_MAINTAIN)
                        #ifdef CONFIG_ARCH_HI6XXX
			if (check_himntn(HIMNTN_PRESS_KEY_TO_FASTBOOT)) {
				if ((VOL_UPDOWN_PRESS & gpio_key_vol_updown_press_get()) == VOL_UPDOWN_PRESS) {
					gpio_key_vol_updown_press_set_zero();
					if(is_gpio_key_vol_updown_pressed()) {
						systemError(0x25, EXCH_S_LOGDUMP, 0,0,0);
					}
				}
			}
			#elif defined(CONFIG_HISI_3635)
				if(is_fastboot_dumpmem_enable())
					if ((VOL_UPDOWN_PRESS & gpio_key_vol_updown_press_get()) == VOL_UPDOWN_PRESS) {
						gpio_key_vol_updown_press_set_zero();
						if(is_gpio_key_vol_updown_pressed()) {
							pr_info("[%s]Powerkey+VolUp_key+VolDn_key\n", __FUNCTION__);
							#ifdef CONFIG_HISI_REBOOT_TYPE
							set_watchdog_resetflag();
							#endif
							emergency_restart();
					}
				}
 			#endif
                        #endif
			input_report_key(info->idev, KEY_POWER, POWER_KEY_RELEASE);
			input_sync(info->idev);
	} else if (info->irq[2] == irq) {
			pr_info("[%s]response long press 1s interrupt!\n", __FUNCTION__);
			input_report_key(info->idev, KEY_POWER, POWER_KEY_PRESS);
			input_sync(info->idev);
	} else if (irq == info->irq[3]) {
		pr_info("[%s]response long press 8s interrupt!\n", __FUNCTION__);
	} else if (irq == info->irq[4]) {
		pr_info("[%s]response long press 10s interrupt!\n", __FUNCTION__);
	} else {
			pr_err("[%s]invalid irq %d!\n", __FUNCTION__, irq);
	}

	return IRQ_HANDLED;
}
コード例 #20
0
static irqreturn_t button_interrupt(int irq, void *dummy) { input_report_key(button_dev, BTN_0, inb(BUTTON_PORT) & 1); input_sync(button_dev); 
return IRQ_HANDLED; }
コード例 #21
0
static void adp5588_work_func( struct work_struct *work)
{
    int rc,i;
    uint8_t reg=ADP5588_REG_KEY_EVENTA;
    struct adp5588_keypad_data *kp = container_of(work, struct adp5588_keypad_data, work);
    struct i2c_client *client=kp->client;
    uint8_t  scan_code;


    /* set  read address */

    I2C_MUTEX_LOCK;

    if ((rc = i2c_master_send(client, &reg, 1)) <0)
    {
        dev_err(&client->dev," %s(%s):i2c_master_send error %d\n",
                __FILE__, __FUNCTION__, rc);
        /* I2c Write error  .  exit now , enable IRQ and read again if IRQ pin  still low */

    } else {

        /* read scancodes until queue is empty */
        i=0;
        do {
            scan_code =ADP5588_KEY_FIFO_EMPTY;

            if ((rc = i2c_master_recv(client, &scan_code,1 )) < 0 )
            {
                dev_err(&client->dev," %s(%s):i2c_master_recv error %d\n",
                        __FILE__, __FUNCTION__, rc);
                break;
            }

            if( scan_code != ADP5588_KEY_FIFO_EMPTY )
            {
                kp->last_key = ADP5588_KEY_CODE & scan_code ;
                kp->last_key_state  = !!(ADP5588_KEY_RELEASE & scan_code);

                dev_dbg(&client->dev,"ADP5588 got scancode %d ,keycode 0x%x ( %d ) state %d \n",

                        scan_code, kp->last_key, kp->last_key,kp->last_key_state );
                if(  kp->last_key == ADP5588_GPIO_KEY )
                {
                    /* got   RINGER/SILENCE  switch event */
                    adp5588_data.ringer_switch = kp->last_key_state;
                    switch_set_state(&adp5588_data.sw_mute_dev, !adp5588_data.ringer_switch);
                } else {
                    /* got   regular key event */
                    input_report_key(kp->input_dev, kp->last_key, kp->last_key_state);
                }

                //  Sync is removed.  It does not required  for key event
                //	  input_sync(kp->input_dev);
            } else  if( i == 0 ) { /*IRQ without the code ? , must be  key release  HW problem , Wait  5ms  */

                clk_busy_wait(5000);
            }

        } while( scan_code && (i++ <10) );
    }
    I2C_MUTEX_UNLOCK;

    /* Clear IRQ and enable it */
    if (kp->use_irq) {
        if ( adp5588_clear_irq(client)<0)
        {   /* I2c Problem , do not enable IRQ but wait 1 sec */
            hrtimer_start(&kp->timer, ktime_set(1,0), HRTIMER_MODE_REL);
        } else  enable_irq(client->irq);
    }

}
コード例 #22
0
ファイル: xpad.c プロジェクト: mjduddin/B14CKB1RD_kernel_m8
static void xpad360_process_packet(struct usb_xpad *xpad,
				   u16 cmd, unsigned char *data)
{
	struct input_dev *dev = xpad->dev;

	
	if (xpad->mapping & MAP_DPAD_TO_BUTTONS) {
		
		input_report_key(dev, BTN_TRIGGER_HAPPY1, data[2] & 0x04);
		input_report_key(dev, BTN_TRIGGER_HAPPY2, data[2] & 0x08);
		input_report_key(dev, BTN_TRIGGER_HAPPY3, data[2] & 0x01);
		input_report_key(dev, BTN_TRIGGER_HAPPY4, data[2] & 0x02);
	} else {
		input_report_abs(dev, ABS_HAT0X,
				 !!(data[2] & 0x08) - !!(data[2] & 0x04));
		input_report_abs(dev, ABS_HAT0Y,
				 !!(data[2] & 0x02) - !!(data[2] & 0x01));
	}

	
	input_report_key(dev, BTN_START,  data[2] & 0x10);
	input_report_key(dev, BTN_SELECT, data[2] & 0x20);

	
	input_report_key(dev, BTN_THUMBL, data[2] & 0x40);
	input_report_key(dev, BTN_THUMBR, data[2] & 0x80);

	
	input_report_key(dev, BTN_A,	data[3] & 0x10);
	input_report_key(dev, BTN_B,	data[3] & 0x20);
	input_report_key(dev, BTN_X,	data[3] & 0x40);
	input_report_key(dev, BTN_Y,	data[3] & 0x80);
	input_report_key(dev, BTN_TL,	data[3] & 0x01);
	input_report_key(dev, BTN_TR,	data[3] & 0x02);
	input_report_key(dev, BTN_MODE,	data[3] & 0x04);

	if (!(xpad->mapping & MAP_STICKS_TO_NULL)) {
		
		input_report_abs(dev, ABS_X,
				 (__s16) le16_to_cpup((__le16 *)(data + 6)));
		input_report_abs(dev, ABS_Y,
				 ~(__s16) le16_to_cpup((__le16 *)(data + 8)));

		
		input_report_abs(dev, ABS_RX,
				 (__s16) le16_to_cpup((__le16 *)(data + 10)));
		input_report_abs(dev, ABS_RY,
				 ~(__s16) le16_to_cpup((__le16 *)(data + 12)));
	}

	
	if (xpad->mapping & MAP_TRIGGERS_TO_BUTTONS) {
		input_report_key(dev, BTN_TL2, data[4]);
		input_report_key(dev, BTN_TR2, data[5]);
	} else {
		input_report_abs(dev, ABS_Z, data[4]);
		input_report_abs(dev, ABS_RZ, data[5]);
	}

	input_sync(dev);
}
コード例 #23
0
void iforce_process_packet(struct iforce *iforce, u16 cmd, unsigned char *data)
{
	struct input_dev *dev = iforce->dev;
	int i;
	static int being_used = 0;

	if (being_used)
		dev_warn(&iforce->dev->dev,
			 "re-entrant call to iforce_process %d\n", being_used);
	being_used++;

#ifdef CONFIG_JOYSTICK_IFORCE_232
	if (HI(iforce->expect_packet) == HI(cmd)) {
		iforce->expect_packet = 0;
		iforce->ecmd = cmd;
		memcpy(iforce->edata, data, IFORCE_MAX_LENGTH);
	}
#endif
	wake_up(&iforce->wait);

	if (!iforce->type) {
		being_used--;
		return;
	}

	switch (HI(cmd)) {

		case 0x01:	/* joystick position data */
		case 0x03:	/* wheel position data */
			if (HI(cmd) == 1) {
				input_report_abs(dev, ABS_X, (__s16) (((__s16)data[1] << 8) | data[0]));
				input_report_abs(dev, ABS_Y, (__s16) (((__s16)data[3] << 8) | data[2]));
				input_report_abs(dev, ABS_THROTTLE, 255 - data[4]);
				if (LO(cmd) >= 8 && test_bit(ABS_RUDDER ,dev->absbit))
					input_report_abs(dev, ABS_RUDDER, (__s8)data[7]);
			} else {
				input_report_abs(dev, ABS_WHEEL, (__s16) (((__s16)data[1] << 8) | data[0]));
				input_report_abs(dev, ABS_GAS,   255 - data[2]);
				input_report_abs(dev, ABS_BRAKE, 255 - data[3]);
			}

			input_report_abs(dev, ABS_HAT0X, iforce_hat_to_axis[data[6] >> 4].x);
			input_report_abs(dev, ABS_HAT0Y, iforce_hat_to_axis[data[6] >> 4].y);

			for (i = 0; iforce->type->btn[i] >= 0; i++)
				input_report_key(dev, iforce->type->btn[i], data[(i >> 3) + 5] & (1 << (i & 7)));

			/* If there are untouched bits left, interpret them as the second hat */
			if (i <= 8) {
				int btns = data[6];
				if (test_bit(ABS_HAT1X, dev->absbit)) {
					if (btns & 8) input_report_abs(dev, ABS_HAT1X, -1);
					else if (btns & 2) input_report_abs(dev, ABS_HAT1X, 1);
					else input_report_abs(dev, ABS_HAT1X, 0);
				}
				if (test_bit(ABS_HAT1Y, dev->absbit)) {
					if (btns & 1) input_report_abs(dev, ABS_HAT1Y, -1);
					else if (btns & 4) input_report_abs(dev, ABS_HAT1Y, 1);
					else input_report_abs(dev, ABS_HAT1Y, 0);
				}
			}

			input_sync(dev);

			break;

		case 0x02:	/* status report */
			input_report_key(dev, BTN_DEAD, data[0] & 0x02);
			input_sync(dev);

			/* Check if an effect was just started or stopped */
			i = data[1] & 0x7f;
			if (data[1] & 0x80) {
				if (!test_and_set_bit(FF_CORE_IS_PLAYED, iforce->core_effects[i].flags)) {
					/* Report play event */
					input_report_ff_status(dev, i, FF_STATUS_PLAYING);
				}
			} else if (test_and_clear_bit(FF_CORE_IS_PLAYED, iforce->core_effects[i].flags)) {
				/* Report stop event */
				input_report_ff_status(dev, i, FF_STATUS_STOPPED);
			}
			if (LO(cmd) > 3) {
				int j;
				for (j = 3; j < LO(cmd); j += 2)
					mark_core_as_ready(iforce, data[j] | (data[j+1]<<8));
			}
			break;
	}
	being_used--;
}
コード例 #24
0
ファイル: rk28_mid_bm999.c プロジェクト: Tigrouzen/k1099
static void rk28_adkeyscan_timer(unsigned long data)
{
	unsigned int ADKEY1,code = 0,i;
	/*Enable  AD controller to sample */
	prockAD_button->timer.expires  = jiffies+msecs_to_jiffies(10);
	add_timer(&prockAD_button->timer);
	RockAdcScanning();
	if (ADSampleTimes < 4)
	{
		ADSampleTimes ++;		
		goto scan_io_key;  	/* scan gpio button event*/
	}
	ADSampleTimes = 0;	
	/*Get button value*/
	ADKEY1=get_rock_adc1();
	if(ADKEY1<EmptyADValue)
		printk("\n ADC1 value=%d  \n",ADKEY1);
#if 1	//ffhh
	if((ADKEY1>EmptyADValue)&&(ADKEY1<=InvalidADValue))  
		goto scan_io_key1;
#endif	
	valuecount++;
 	if(valuecount < 2)
		goto scan_code;	
	code=find_rock_adkeycode(ADKEY1,ad1valuetab);
	valuecount = 2;	
	goto scan_code;  ///scan_code;	
scan_io_key1:
	valuecount = 0;	

scan_code:	
	if((g_code == 0) && (code == 0)){
	    goto scan_io_key; 
	}
	///DBG("\n key button PE2 == %d  \n",GPIOGetPinLevel(GPIOPortE_Pin2)); 
	if(code != 0){
		if(valuecount<2)
			goto scan_io_key; 
		if(g_code == 0){
			g_code = code;
			DBG("\n %s::%d rock adc1 key scan ,find press down a key=%d  \n",__func__,__LINE__,g_code);
			input_report_key(prockAD_button->input_dev,g_code,1);
	        	input_sync(prockAD_button->input_dev);
	        	goto scan_io_key; 
		}else{
			if(g_code != code){
				DBG("\n %s::%d rock adc1 key scan ,find press up a key=%d  \n",__func__,__LINE__,g_code);
				input_report_key(prockAD_button->input_dev,g_code,0);
	            		input_sync(prockAD_button->input_dev);
	            		DBG("\n %s::%d rock adc1 key scan ,find press down a key=%d  \n",__func__,__LINE__,code);
	            		input_report_key(prockAD_button->input_dev,code,1);
	            		input_sync(prockAD_button->input_dev);
	            		g_code = code;
	           		goto scan_io_key; 
			}
		}
    
    	}
	if((g_code != 0)&&(code == 0)&&(ADSampleTimes == 0)){
		DBG("\n %s::%d rock adc1 key scan ,find press up a key=%d  \n",__func__,__LINE__,g_code);
	    	input_report_key(prockAD_button->input_dev,g_code,0);
	    	input_sync(prockAD_button->input_dev);
		valuecount = 0;
		g_code = 0;
		goto scan_io_key;
	}
scan_io_key :
    if(g_wake_press)
    {
        pwrscantimes = 0;
        g_wake_press = !GPIOGetPinLevel(WAKEUP_KEY_PORT);
        if(g_wake_press) return;
    }
	if(!GPIOGetPinLevel(GPIOPortE_Pin2))
	{
		pwrscantimes += 1;
		if(pwrscantimes == (SEC_NUM * ONESEC_TIMES))
		{
			input_report_key(prockAD_button->input_dev,ENDCALL,1);
			input_sync(prockAD_button->input_dev);
			DBG("the kernel come to power down!!!\n");
		
		}
		if(pwrscantimes ==( (SEC_NUM + 1)* ONESEC_TIMES))
		{
			pwrscantimes = 0;
			input_report_key(prockAD_button->input_dev,ENDCALL,0);
			input_sync(prockAD_button->input_dev);
			DBG("the kernel come to power up!!!\n");
		
		}
		return ;
	}
	
	if( pwrscantimes > SLEEP_TIME)
	{
		pwrscantimes = 0;
        printk("========== %s: g_enable_sleep=%d\n", __FUNCTION__, g_enable_sleep);
		if(g_enable_sleep)
		{
			input_report_key(prockAD_button->input_dev,AD1KEY5,1);
			input_sync(prockAD_button->input_dev);
			input_report_key(prockAD_button->input_dev,AD1KEY5,0);
			input_sync(prockAD_button->input_dev);
			
		}
		 rk28printk("\n%s^^^^Wake Up ^^^^^!!\n",__FUNCTION__);
	}

}
コード例 #25
0
static void xpad360_process_packet(struct usb_xpad *xpad,
				   u16 cmd, unsigned char *data)
{
	struct input_dev *dev = xpad->dev;

	/* digital pad */
	if (xpad->mapping & MAP_DPAD_TO_BUTTONS) {
		/* dpad as buttons (left, right, up, down) */
		input_report_key(dev, BTN_TRIGGER_HAPPY1, data[2] & 0x04);
		input_report_key(dev, BTN_TRIGGER_HAPPY2, data[2] & 0x08);
		input_report_key(dev, BTN_TRIGGER_HAPPY3, data[2] & 0x01);
		input_report_key(dev, BTN_TRIGGER_HAPPY4, data[2] & 0x02);
	} else {
		input_report_abs(dev, ABS_HAT0X,
				 !!(data[2] & 0x08) - !!(data[2] & 0x04));
		input_report_abs(dev, ABS_HAT0Y,
				 !!(data[2] & 0x02) - !!(data[2] & 0x01));
	}

	/* start/back buttons */
	input_report_key(dev, BTN_START,  data[2] & 0x10);
	input_report_key(dev, BTN_SELECT, data[2] & 0x20);

	/* stick press left/right */
	input_report_key(dev, BTN_THUMBL, data[2] & 0x40);
	input_report_key(dev, BTN_THUMBR, data[2] & 0x80);

	/* buttons A,B,X,Y,TL,TR and MODE */
	input_report_key(dev, BTN_A,	data[3] & 0x10);
	input_report_key(dev, BTN_B,	data[3] & 0x20);
	input_report_key(dev, BTN_X,	data[3] & 0x40);
	input_report_key(dev, BTN_Y,	data[3] & 0x80);
	input_report_key(dev, BTN_TL,	data[3] & 0x01);
	input_report_key(dev, BTN_TR,	data[3] & 0x02);
	input_report_key(dev, BTN_MODE,	data[3] & 0x04);

	if (!(xpad->mapping & MAP_STICKS_TO_NULL)) {
		/* left stick */
		input_report_abs(dev, ABS_X,
				 (__s16) le16_to_cpup((__le16 *)(data + 6)));
		input_report_abs(dev, ABS_Y,
				 ~(__s16) le16_to_cpup((__le16 *)(data + 8)));

		/* right stick */
		input_report_abs(dev, ABS_RX,
				 (__s16) le16_to_cpup((__le16 *)(data + 10)));
		input_report_abs(dev, ABS_RY,
				 ~(__s16) le16_to_cpup((__le16 *)(data + 12)));
	}

	/* triggers left/right */
	if (xpad->mapping & MAP_TRIGGERS_TO_BUTTONS) {
		input_report_key(dev, BTN_TL2, data[4]);
		input_report_key(dev, BTN_TR2, data[5]);
	} else {
		input_report_abs(dev, ABS_Z, data[4]);
		input_report_abs(dev, ABS_RZ, data[5]);
	}

	input_sync(dev);
}
コード例 #26
0
//input key conversion
void input_report_rcp_key(uint8_t rcp_keycode, int up_down)
{
    rcp_keycode &= 0x7F;

    TX_DEBUG_PRINT( ("\nupdown = %d " , up_down));
    switch ( rcp_keycode )
    {
    case MHL_RCP_CMD_SELECT:// error
        input_report_key(kpd_input_dev, KEY_SELECT, up_down);
        TX_DEBUG_PRINT(( "\nSelect received\n\n" ));
        break;
    case MHL_RCP_CMD_UP:
        input_report_key(kpd_input_dev, KEY_UP, up_down);
        TX_DEBUG_PRINT(( "\nUp received\n\n" ));
        break;
    case MHL_RCP_CMD_DOWN:
        input_report_key(kpd_input_dev, KEY_DOWN, up_down);
        TX_DEBUG_PRINT(( "\nDown received\n\n" ));
        break;
    case MHL_RCP_CMD_LEFT:
        input_report_key(kpd_input_dev, KEY_LEFT, up_down);
        TX_DEBUG_PRINT(( "\nLeft received\n\n" ));
        break;
    case MHL_RCP_CMD_RIGHT:
        input_report_key(kpd_input_dev, KEY_RIGHT, up_down);
        TX_DEBUG_PRINT(( "\nRight received\n\n" ));
        break;
    case MHL_RCP_CMD_ROOT_MENU:
        input_report_key(kpd_input_dev, KEY_MENU, up_down);
        TX_DEBUG_PRINT(( "\nRoot Menu received\n\n" ));
        break;
    case MHL_RCP_CMD_EXIT:
        input_report_key(kpd_input_dev, KEY_BACK, up_down);
        TX_DEBUG_PRINT(( "\nExit received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_0:
        input_report_key(kpd_input_dev, KEY_0, up_down);
        TX_DEBUG_PRINT(( "\nNumber 0 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_1:
        input_report_key(kpd_input_dev, KEY_1, up_down);
        TX_DEBUG_PRINT(( "\nNumber 1 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_2:
        input_report_key(kpd_input_dev, KEY_2, up_down);
        TX_DEBUG_PRINT(( "\nNumber 2 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_3:
        input_report_key(kpd_input_dev, KEY_3, up_down);
        TX_DEBUG_PRINT(( "\nNumber 3 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_4:
        input_report_key(kpd_input_dev, KEY_4, up_down);
        TX_DEBUG_PRINT(( "\nNumber 4 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_5:
        input_report_key(kpd_input_dev, KEY_5, up_down);
        TX_DEBUG_PRINT(( "\nNumber 5 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_6:
        input_report_key(kpd_input_dev, KEY_6, up_down);
        TX_DEBUG_PRINT(( "\nNumber 6 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_7:
        input_report_key(kpd_input_dev, KEY_7, up_down);
        TX_DEBUG_PRINT(( "\nNumber 7 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_8:
        input_report_key(kpd_input_dev, KEY_8, up_down);
        TX_DEBUG_PRINT(( "\nNumber 8 received\n\n" ));
        break;
    case MHL_RCP_CMD_NUM_9:
        input_report_key(kpd_input_dev, KEY_9, up_down);
        TX_DEBUG_PRINT(( "\nNumber 9 received\n\n" ));
        break;
    case MHL_RCP_CMD_DOT:
        input_report_key(kpd_input_dev, KEY_DOT, up_down);
        TX_DEBUG_PRINT(( "\nDot received\n\n" ));
        break;
    case MHL_RCP_CMD_ENTER:
        input_report_key(kpd_input_dev, KEY_ENTER, up_down);
        TX_DEBUG_PRINT(( "\nEnter received\n\n" ));
        break;
    case MHL_RCP_CMD_CLEAR:
        input_report_key(kpd_input_dev, KEY_CLEAR, up_down);
        TX_DEBUG_PRINT(( "\nClear received\n\n" ));
        break;
    case MHL_RCP_CMD_SOUND_SELECT:
        input_report_key(kpd_input_dev, KEY_SOUND, up_down);
        TX_DEBUG_PRINT(( "\nSound Select received\n\n" ));
        break;
    case MHL_RCP_CMD_PLAY:
        input_report_key(kpd_input_dev, KEY_PLAY, up_down);
        TX_DEBUG_PRINT(( "\nPlay received\n\n" ));
        break;
    case MHL_RCP_CMD_PAUSE:
        //input_report_key(kpd_input_dev, KEY_PAUSE, up_down);
        input_report_key(kpd_input_dev, KEY_PAUSECD, up_down);

        TX_DEBUG_PRINT(( "\nPause received\n\n" ));
        break;
    case MHL_RCP_CMD_STOP:
        input_report_key(kpd_input_dev, KEY_STOP, up_down);
        TX_DEBUG_PRINT(( "\nStop received\n\n" ));
        break;
    case MHL_RCP_CMD_FAST_FWD:
        input_report_key(kpd_input_dev, KEY_FASTFORWARD, up_down);
        input_report_key(kpd_input_dev, KEY_FASTFORWARD, up_down);
        TX_DEBUG_PRINT(( "\nFastfwd received\n\n" ));
        break;
    case MHL_RCP_CMD_REWIND:
        input_report_key(kpd_input_dev, KEY_REWIND, up_down);
        TX_DEBUG_PRINT(( "\nRewind received\n\n" ));
        break;
    case MHL_RCP_CMD_EJECT:
        input_report_key(kpd_input_dev, KEY_EJECTCD, up_down);
        TX_DEBUG_PRINT(( "\nEject received\n\n" ));
        break;
    case MHL_RCP_CMD_FWD:
        //input_report_key(kpd_input_dev, KEY_FORWARD, up_down);//next song
        input_report_key(kpd_input_dev, KEY_NEXTSONG, up_down);
        TX_DEBUG_PRINT(( "\nNext song received\n\n" ));
        break;
    case MHL_RCP_CMD_BKWD:
        //input_report_key(kpd_input_dev, KEY_BACK, up_down);//previous song
        input_report_key(kpd_input_dev, KEY_PREVIOUSSONG, up_down);
        TX_DEBUG_PRINT(( "\nPrevious song received\n\n" ));
        break;
    case MHL_RCP_CMD_PLAY_FUNC:
        //input_report_key(kpd_input_dev, KEY_PL, up_down);
		input_report_key(kpd_input_dev, KEY_PLAY, up_down);
        TX_DEBUG_PRINT(( "\nPlay Function received\n\n" ));
    break;
    case MHL_RCP_CMD_PAUSE_PLAY_FUNC:
        input_report_key(kpd_input_dev, KEY_PLAYPAUSE, up_down);
        TX_DEBUG_PRINT(( "\nPause_Play Function received\n\n" ));
        break;
    case MHL_RCP_CMD_STOP_FUNC:
        input_report_key(kpd_input_dev, KEY_STOP, up_down);
        TX_DEBUG_PRINT(( "\nStop Function received\n\n" ));
        break;
    case MHL_RCP_CMD_F1:
        input_report_key(kpd_input_dev, KEY_F1, up_down);
        TX_DEBUG_PRINT(( "\nF1 received\n\n" ));
        break;
    case MHL_RCP_CMD_F2:
        input_report_key(kpd_input_dev, KEY_F2, up_down);
        TX_DEBUG_PRINT(( "\nF2 received\n\n" ));
        break;
    case MHL_RCP_CMD_F3:
        input_report_key(kpd_input_dev, KEY_F3, up_down);
        TX_DEBUG_PRINT(( "\nF3 received\n\n" ));
        break;
    case MHL_RCP_CMD_F4:
        input_report_key(kpd_input_dev, KEY_F4, up_down);
        TX_DEBUG_PRINT(( "\nF4 received\n\n" ));
        break;
    case MHL_RCP_CMD_F5:
        input_report_key(kpd_input_dev, KEY_F5, up_down);
        TX_DEBUG_PRINT(( "\nF5 received\n\n" ));
        break;
    default:
        break;
    }
		
    //added  for improving mhl RCP start
    input_sync(kpd_input_dev);
    //added  for improving mhl RCP end
}
static irqreturn_t touchkey_interrupt(int irq, void *dev_id)
{
	struct touchkey_i2c *tkey_i2c = dev_id;
    static const int ledCmd[] = {TK_CMD_LED_ON, TK_CMD_LED_OFF};
	u8 data[3];
	int ret;
	int retry = 10;
	int keycode_type = 0;
	int pressed;

	set_touchkey_debug('a');

	retry = 3;
	while (retry--) {
		ret = i2c_touchkey_read(tkey_i2c->client, KEYCODE_REG, data, 3);
		if (!ret)
			break;
		else {
			pr_debug("[TouchKey] i2c read failed, ret:%d, retry: %d\n",
			       ret, retry);
			continue;
		}
	}
	if (ret < 0)
		return IRQ_HANDLED;

	set_touchkey_debug(data[0]);

	keycode_type = (data[0] & TK_BIT_KEYCODE);
	pressed = !(data[0] & TK_BIT_PRESS_EV);

	if (keycode_type <= 0 || keycode_type >= touchkey_count) {
		pr_debug("[Touchkey] keycode_type err\n");
		return IRQ_HANDLED;
	}

	if (pressed) {
		set_touchkey_debug('P');

        // enable lights on keydown
        if (touch_led_disabled == 0) {
            if (touchkey_led_status == TK_CMD_LED_OFF) {
                pr_debug("[Touchkey] %s: keydown - LED ON\n", __func__);
                i2c_touchkey_write(tkey_i2c->client, (u8 *) &ledCmd[0], 1);
                touchkey_led_status = TK_CMD_LED_ON;
            }
            if (timer_pending(&touch_led_timer) == 1) {
                mod_timer(&touch_led_timer, jiffies + (HZ * touch_led_timeout));
            }
        }
        
    } else {
        // touch led timeout on keyup
        if (touch_led_disabled == 0) {
            if (timer_pending(&touch_led_timer) == 0) {
                pr_debug("[Touchkey] %s: keyup - add_timer\n", __func__);
                touch_led_timer.expires = jiffies + (HZ * touch_led_timeout);
                add_timer(&touch_led_timer);
            } else {
                mod_timer(&touch_led_timer, jiffies + (HZ * touch_led_timeout));
            }
        }
    }

	if (get_tsp_status() && pressed)
		pr_debug("[TouchKey] touchkey pressed but don't send event because touch is pressed.\n");
	else {
		input_report_key(tkey_i2c->input_dev,
				 touchkey_keycode[keycode_type], pressed);
		input_sync(tkey_i2c->input_dev);
		/* pr_debug("[TouchKey] keycode:%d pressed:%d\n",
		   touchkey_keycode[keycode_index], pressed); */

		#if defined(CONFIG_TARGET_LOCALE_KOR)
		if (g_debug_tkey == true) {
			pr_debug("[TouchKey] keycode[%d]=%d pressed:%d\n",
			keycode_type, touchkey_keycode[keycode_type], pressed);
		} else {
			pr_debug("[TouchKey] pressed:%d\n", pressed);
		}
		#endif
	}
	set_touchkey_debug('A');
	return IRQ_HANDLED;
}
コード例 #28
0
void  touchkey_work_func(struct work_struct * p)
{
	u8 data[3];
	int ret;
	int retry = 10;

	set_touchkey_debug('a');
	if (!gpio_get_value(_3_GPIO_TOUCH_INT)) {
		#ifdef CONFIG_CPU_FREQ
		set_dvfs_target_level(LEV_800MHZ);
		#endif
		ret = i2c_touchkey_read(KEYCODE_REG, data, 1);
		set_touchkey_debug(data[0]);
		if ((data[0] & ESD_STATE_BIT) || (ret != 0)) {
			printk
			    ("ESD_STATE_BIT set or I2C fail: data: %d, retry: %d\n",
			     data[0], retry);
			//releae key 
			input_report_key(touchkey_driver->input_dev,
					 touchkey_keycode[1], 0);
			input_report_key(touchkey_driver->input_dev,
					 touchkey_keycode[2], 0);
			retry = 10;
			while (retry--) {
				gpio_direction_output(_3_GPIO_TOUCH_EN, 0);
				mdelay(300);
				init_hw();
				if (i2c_touchkey_read(KEYCODE_REG, data, 3) >=
				    0) {
					printk("%s touchkey init success\n",
					       __func__);
					set_touchkey_debug('O');
					enable_irq(IRQ_TOUCH_INT);
		return;
	}
				printk("%s %d i2c transfer error retry = %d\n",
				       __func__, __LINE__, retry);
			}
			//touchkey die , do not enable touchkey
			//enable_irq(IRQ_TOUCH_INT);
			touchkey_enable = -1;
			gpio_direction_output(_3_GPIO_TOUCH_EN, 0);
#if !(defined(CONFIG_ARIES_NTT) || defined(CONFIG_S5PC110_CELOX_BOARD))

			gpio_direction_output(_3_GPIO_TOUCH_CE, 0);
#endif
			gpio_direction_output(_3_TOUCH_SDA_28V, 0);
			gpio_direction_output(_3_TOUCH_SCL_28V, 0);
			printk("%s touchkey died\n", __func__);
			set_touchkey_debug('D');
			return;
		}

		if (data[0] & UPDOWN_EVENT_BIT) {
			input_report_key(touchkey_driver->input_dev,
					 touchkey_keycode[data[0] &
							  KEYCODE_BIT], 0);
		input_sync(touchkey_driver->input_dev);
			//printk(" touchkey release keycode: %d\n", touchkey_keycode[data[0] & KEYCODE_BIT]);
			printk(KERN_DEBUG "touchkey release keycode:%d \n",
			       touchkey_keycode[data[0] & KEYCODE_BIT]);

		} else {
			if (touch_state_val == 1) {
				printk(KERN_DEBUG
				       "touchkey pressed but don't send event because touch is pressed. \n");
				set_touchkey_debug('P');
			} else {
				if ((data[0] & KEYCODE_BIT) == 2) {	// if back key is pressed, release multitouch
					//printk("touchkey release tsp input. \n");
					TSP_forced_release();
	}

				input_report_key(touchkey_driver->input_dev,
						 touchkey_keycode[data[0] &
								  KEYCODE_BIT],
						 1);
		input_sync(touchkey_driver->input_dev);
				//printk(" touchkey press keycode: %d\n", touchkey_keycode[data[0] & KEYCODE_BIT]);
				printk(KERN_DEBUG
				       "touchkey press keycode:%d \n",
				       touchkey_keycode[data[0] & KEYCODE_BIT]);
			}
		}
	}
	//clear interrupt
#if defined(CONFIG_S5PC110_CELOX_BOARD)	
	if (readl(gpio_pend_mask_mem) & (0x1 << 5))
		writel(readl(gpio_pend_mask_mem) | (0x1 << 5),
		       gpio_pend_mask_mem);
#else
	if (readl(gpio_pend_mask_mem) & (0x1 << 1))
		writel(readl(gpio_pend_mask_mem) | (0x1 << 1),
		       gpio_pend_mask_mem);
#endif

	set_touchkey_debug('A');
	enable_irq(IRQ_TOUCH_INT);
}
コード例 #29
0
void stm401_irq_wake_work_func(struct work_struct *work)
{
    int err;
    unsigned short irq_status;
    u32 irq2_status;
    uint8_t irq3_status;
    struct stm401_data *ps_stm401 = container_of(work,
                                    struct stm401_data, irq_wake_work);

    dev_dbg(&ps_stm401->client->dev, "stm401_irq_wake_work_func\n");
    mutex_lock(&ps_stm401->lock);

    if (ps_stm401->mode == BOOTMODE)
        goto EXIT_NO_WAKE;

    /* This is to handle the case of receiving an interrupt after
       suspend_late, but before interrupts were globally disabled. If this
       is the case, interrupts might be disabled now, so we cannot handle
       this at this time. suspend_noirq will return BUSY if this happens
       so that we can handle these interrupts. */
    if (ps_stm401->ignore_wakeable_interrupts) {
        dev_info(&ps_stm401->client->dev,
                 "Deferring interrupt work\n");
        ps_stm401->ignored_interrupts++;
        goto EXIT_NO_WAKE;
    }

    stm401_wake(ps_stm401);

    /* read interrupt mask register */
    stm401_cmdbuff[0] = WAKESENSOR_STATUS;
    err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 2);
    if (err < 0) {
        dev_err(&ps_stm401->client->dev, "Reading from stm401 failed\n");
        goto EXIT;
    }
    irq_status = (stm401_readbuff[IRQ_WAKE_MED] << 8)
                 | stm401_readbuff[IRQ_WAKE_LO];

    /* read algorithm interrupt status register */
    stm401_cmdbuff[0] = ALGO_INT_STATUS;
    err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 3);
    if (err < 0) {
        dev_err(&ps_stm401->client->dev, "Reading from stm401 failed\n");
        goto EXIT;
    }
    irq2_status = (stm401_readbuff[IRQ_WAKE_HI] << 16) |
                  (stm401_readbuff[IRQ_WAKE_MED] << 8) |
                  stm401_readbuff[IRQ_WAKE_LO];

    /* read generic interrupt register */
    stm401_cmdbuff[0] = GENERIC_INT_STATUS;
    err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
    if (err < 0) {
        dev_err(&ps_stm401->client->dev, "Reading from stm failed\n");
        goto EXIT;
    }
    irq3_status = stm401_readbuff[0];

    if (ps_stm401->qw_irq_status) {
        irq_status |= ps_stm401->qw_irq_status;
        ps_stm401->qw_irq_status = 0;
    }

    /* First, check for error messages */
    if (irq_status & M_LOG_MSG) {
        stm401_cmdbuff[0] = ERROR_STATUS;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff,
                                    1, ESR_SIZE);
        if (err >= 0) {
            memcpy(stat_string, stm401_readbuff, ESR_SIZE);
            stat_string[ESR_SIZE] = 0;
            dev_err(&ps_stm401->client->dev,
                    "STM401 Error: %s\n", stat_string);
        } else
            dev_err(&ps_stm401->client->dev,
                    "Failed to read error message %d\n", err);
    }

    /* Second, check for a reset request */
    if (irq_status & M_HUB_RESET) {
        unsigned char status;

        if (strnstr(stat_string, "modality", ESR_SIZE))
            status = 0x01;
        else if (strnstr(stat_string, "Algo", ESR_SIZE))
            status = 0x02;
        else if (strnstr(stat_string, "Watchdog", ESR_SIZE))
            status = 0x03;
        else
            status = 0x04;

        stm401_as_data_buffer_write(ps_stm401, DT_RESET, &status, 1, 0);

        stm401_reset_and_init();
        dev_err(&ps_stm401->client->dev, "STM401 requested a reset\n");
        goto EXIT;
    }

    /* Check all other status bits */
    if (irq_status & M_DOCK) {
        int state;

        dev_err(&ps_stm401->client->dev,
                "Invalid M_DOCK bit set. irq_status = 0x%06x\n",
                irq_status);

        stm401_cmdbuff[0] = DOCK_DATA;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading Dock state failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_DOCK,
                                    stm401_readbuff, 1, 0);
        state = stm401_readbuff[DOCK_STATE];
        if (ps_stm401->dsdev.dev != NULL)
            switch_set_state(&ps_stm401->dsdev, state);
        if (ps_stm401->edsdev.dev != NULL)
            switch_set_state(&ps_stm401->edsdev, state);

        dev_dbg(&ps_stm401->client->dev, "Dock status:%d\n", state);
    }
    if (irq_status & M_PROXIMITY) {
        stm401_cmdbuff[0] = PROXIMITY;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading prox from stm401 failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_PROX,
                                    stm401_readbuff, 1, 0);

        dev_dbg(&ps_stm401->client->dev,
                "Sending Proximity distance %d\n",
                stm401_readbuff[PROX_DISTANCE]);
    }
    if (irq_status & M_TOUCH) {
        if (stm401_display_handle_touch_locked(ps_stm401) < 0)
            goto EXIT;
    }
    if (irq_status & M_COVER) {
        int state;
        stm401_cmdbuff[0] = COVER_DATA;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading Cover state failed\n");
            goto EXIT;
        }

        state = stm401_readbuff[COVER_STATE];
        if (state > 0)
            state = 1;

        input_report_switch(ps_stm401->input_dev, SW_LID, state);
        input_sync(ps_stm401->input_dev);

        dev_dbg(&ps_stm401->client->dev, "Cover status: %d\n", state);
    }
    if (irq_status & M_QUICKPEEK) {
        if (stm401_display_handle_quickpeek_locked(ps_stm401,
                irq_status == M_QUICKPEEK) < 0)
            goto EXIT;
    }
    if (irq_status & M_FLATUP) {
        stm401_cmdbuff[0] = FLAT_DATA;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading flat data from stm401 failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_FLAT_UP,
                                    stm401_readbuff, 1, 0);

        dev_dbg(&ps_stm401->client->dev, "Sending Flat up %d\n",
                stm401_readbuff[FLAT_UP]);
    }
    if (irq_status & M_FLATDOWN) {
        stm401_cmdbuff[0] = FLAT_DATA;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading flat data from stm401 failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_FLAT_DOWN,
                                    stm401_readbuff, 1, 0);

        dev_dbg(&ps_stm401->client->dev, "Sending Flat down %d\n",
                stm401_readbuff[FLAT_DOWN]);
    }
    if (irq_status & M_STOWED) {
        stm401_cmdbuff[0] = STOWED;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading stowed from stm401 failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_STOWED,
                                    stm401_readbuff, 1, 0);

        dev_dbg(&ps_stm401->client->dev,
                "Sending Stowed status %d\n", stm401_readbuff[STOWED]);
    }
    if (irq_status & M_CAMERA_ACT) {
        stm401_cmdbuff[0] = CAMERA;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 2);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading camera data from stm failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_CAMERA_ACT,
                                    stm401_readbuff, 2, 0);

        dev_dbg(&ps_stm401->client->dev,
                "Sending Camera: %d\n", STM16_TO_HOST(CAMERA_VALUE));

        input_report_key(ps_stm401->input_dev, KEY_CAMERA, 1);
        input_report_key(ps_stm401->input_dev, KEY_CAMERA, 0);
        input_sync(ps_stm401->input_dev);
        dev_dbg(&ps_stm401->client->dev,
                "Report camkey toggle\n");
    }
    if (irq_status & M_NFC) {
        stm401_cmdbuff[0] = NFC;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 1);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading nfc data from stm failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_NFC,
                                    stm401_readbuff, 1, 0);

        dev_dbg(&ps_stm401->client->dev,
                "Sending NFC value: %d\n", stm401_readbuff[NFC_VALUE]);

    }
    if (irq_status & M_SIM) {
        stm401_cmdbuff[0] = SIM;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 2);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading sig_motion data from stm failed\n");
            goto EXIT;
        }
        stm401_as_data_buffer_write(ps_stm401, DT_SIM,
                                    stm401_readbuff, 2, 0);

        /* This is one shot sensor */
        stm401_g_wake_sensor_state &= (~M_SIM);

        dev_dbg(&ps_stm401->client->dev, "Sending SIM Value=%d\n",
                STM16_TO_HOST(SIM_DATA));
    }
    if (irq_status & M_CHOPCHOP) {
        stm401_cmdbuff[0] = CHOPCHOP;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1, 2);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading chopchop data from stm failed\n");
            goto EXIT;
        }

        stm401_as_data_buffer_write(ps_stm401, DT_CHOPCHOP,
                                    stm401_readbuff, 2, 0);

        dev_dbg(&ps_stm401->client->dev, "ChopChop triggered. Gyro aborts=%d\n",
                STM16_TO_HOST(CHOPCHOP_DATA));
    }
    if (irq2_status & M_MMOVEME) {
        unsigned char status;
        /* Client recieving action will be upper 2 most significant */
        /* bits of the least significant byte of status. */
        status = (irq2_status & STM401_CLIENT_MASK) | M_MMOVEME;
        stm401_ms_data_buffer_write(ps_stm401, DT_MMMOVE, &status, 1);

        dev_dbg(&ps_stm401->client->dev,
                "Sending meaningful movement event\n");
    }
    if (irq2_status & M_NOMMOVE) {
        unsigned char status;
        /* Client recieving action will be upper 2 most significant */
        /* bits of the least significant byte of status. */
        status = (irq2_status & STM401_CLIENT_MASK) | M_NOMMOVE;
        stm401_ms_data_buffer_write(ps_stm401, DT_NOMOVE, &status, 1);

        dev_dbg(&ps_stm401->client->dev,
                "Sending no meaningful movement event\n");
    }
    if (irq2_status & M_ALGO_MODALITY) {
        stm401_cmdbuff[0] =
            stm401_algo_info[STM401_IDX_MODALITY].evt_register;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1,
                                    STM401_EVT_SZ_TRANSITION);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading modality event failed\n");
            goto EXIT;
        }
        stm401_readbuff[ALGO_TYPE] = STM401_IDX_MODALITY;
        stm401_ms_data_buffer_write(ps_stm401, DT_ALGO_EVT,
                                    stm401_readbuff, 8);
        dev_dbg(&ps_stm401->client->dev, "Sending modality event\n");
    }
    if (irq2_status & M_ALGO_ORIENTATION) {
        stm401_cmdbuff[0] =
            stm401_algo_info[STM401_IDX_ORIENTATION].evt_register;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1,
                                    STM401_EVT_SZ_TRANSITION);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading orientation event failed\n");
            goto EXIT;
        }
        stm401_readbuff[ALGO_TYPE] = STM401_IDX_ORIENTATION;
        stm401_ms_data_buffer_write(ps_stm401, DT_ALGO_EVT,
                                    stm401_readbuff, 8);
        dev_dbg(&ps_stm401->client->dev, "Sending orientation event\n");
    }
    if (irq2_status & M_ALGO_STOWED) {
        stm401_cmdbuff[0] =
            stm401_algo_info[STM401_IDX_STOWED].evt_register;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1,
                                    STM401_EVT_SZ_TRANSITION);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading stowed event failed\n");
            goto EXIT;
        }
        stm401_readbuff[ALGO_TYPE] = STM401_IDX_STOWED;
        stm401_ms_data_buffer_write(ps_stm401, DT_ALGO_EVT,
                                    stm401_readbuff, 8);
        dev_dbg(&ps_stm401->client->dev, "Sending stowed event\n");
    }
    if (irq2_status & M_ALGO_ACCUM_MODALITY) {
        stm401_cmdbuff[0] =
            stm401_algo_info[STM401_IDX_ACCUM_MODALITY]
            .evt_register;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1,
                                    STM401_EVT_SZ_ACCUM_STATE);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading accum modality event failed\n");
            goto EXIT;
        }
        stm401_readbuff[ALGO_TYPE] = STM401_IDX_ACCUM_MODALITY;
        stm401_ms_data_buffer_write(ps_stm401, DT_ALGO_EVT,
                                    stm401_readbuff, 8);
        dev_dbg(&ps_stm401->client->dev, "Sending accum modality event\n");
    }
    if (irq2_status & M_ALGO_ACCUM_MVMT) {
        stm401_cmdbuff[0] =
            stm401_algo_info[STM401_IDX_ACCUM_MVMT].evt_register;
        err = stm401_i2c_write_read(ps_stm401, stm401_cmdbuff, 1,
                                    STM401_EVT_SZ_ACCUM_MVMT);
        if (err < 0) {
            dev_err(&ps_stm401->client->dev,
                    "Reading accum mvmt event failed\n");
            goto EXIT;
        }
        stm401_readbuff[ALGO_TYPE] = STM401_IDX_ACCUM_MVMT;
        stm401_ms_data_buffer_write(ps_stm401, DT_ALGO_EVT,
                                    stm401_readbuff, 8);
        dev_dbg(&ps_stm401->client->dev, "Sending accum mvmt event\n");
    }
    if (irq2_status & M_IR_WAKE_GESTURE) {
        err = stm401_process_ir_gesture(ps_stm401);
        if (err < 0)
            goto EXIT;
    }
    if (irq3_status & M_GENERIC_INTRPT) {

        dev_err(&ps_stm401->client->dev,
                "Invalid M_GENERIC_INTRPT bit set. irq_status = 0x%06x\n",
                irq_status);

        /* x (data1) : irq3_status */
        stm401_ms_data_buffer_write(ps_stm401, DT_GENERIC_INT,
                                    &irq3_status, 1);
        dev_dbg(&ps_stm401->client->dev,
                "Sending generic interrupt event:%d\n", irq3_status);
    }

EXIT:
    stm401_sleep(ps_stm401);
EXIT_NO_WAKE:
    mutex_unlock(&ps_stm401->lock);
}
コード例 #30
0
static void st1232_ts_update_pen_state(struct st1232_ts_data *ts, int x, int y, int pressure)
{
	int i=0;/*
	if(NULL!=msm_7k_handset_get_input_dev())
		kpdev =(struct input_dev *) msm_7k_handset_get_input_dev();
	else
	{
		printk("[bing]msm_7k_handset_get_input_dev=NULL \r\n");
		goto err;
	}*/
	//printk("[Bing][%s] x=%d, y=%d, p=%d keyregister=%d ,tpversion=%d \r\n", __func__, x, y, pressure,keyregister,tpversion);
	//printk("[bing]kpdev=%d ,KEY_HOME=%d KEY_SEARCH=%d KEY_BACK=%d KEY_MENU=%d ,pressure=%d\r\n",kpdev,KEY_HOME,KEY_SEARCH,KEY_BACK,KEY_MENU,pressure);
	if(y<=480)
	{	
        	for (i = 0; i < st1232_ts->prev_touches; i++) {
        		input_report_abs(st1232_ts->input_dev, ABS_MT_TOUCH_MAJOR, 0);
        		input_report_abs(st1232_ts->input_dev, ABS_MT_WIDTH_MAJOR, 0);
        		input_mt_sync(st1232_ts->input_dev);
        	}
        	st1232_ts->prev_touches = 0;
        	input_sync(st1232_ts->input_dev);
	}

		 if(tpversion>=1) //Herman
		{
			if(keyregister==1)
			{	
				input_report_key(st1232_ts->input_dev, KEY_HOME, pressure);	
				//printk("[bing]KEY_HOME,keyregister=%d \r\n",keyregister);
			}
			else if(keyregister==2)
			{	
				input_report_key(st1232_ts->input_dev, KEY_SEARCH, pressure);
				//printk("[bing]KEY_SEARCH,keyregister=%d \r\n",keyregister);
			}
			else if(keyregister==4)
			{	
				input_report_key(st1232_ts->input_dev, KEY_BACK, pressure);		
				//printk("[bing]KEY_BACK,keyregister=%d \r\n",keyregister);
			}
			else if(keyregister==8)
			{
				input_report_key(st1232_ts->input_dev, KEY_MENU, pressure);
				//printk("[bing]KEY_MENU,keyregister=%d \r\n",keyregister);
			}
        		input_sync(st1232_ts->input_dev);
		}	
 		else if(tpversion==0)
 		{
 	 			if(y>490)			
 	 			{
					if(x>0&&x<=80)
					{	
						input_report_key(st1232_ts->input_dev, KEY_HOME, pressure);	
						//printk("[bing]KEY_HOME \r\n");
					}
					else if(x>80&&x<=150)
					{
						input_report_key(st1232_ts->input_dev, KEY_SEARCH, pressure);
						//printk("[bing]KEY_SEARCH \r\n");
					}
					else if(x>150&&x<=260)
					{	
						input_report_key(st1232_ts->input_dev, KEY_BACK, pressure);		
						//printk("[bing]KEY_BACK \r\n");
					}
					else if(x>260)
					{
						input_report_key(st1232_ts->input_dev, KEY_MENU, pressure);
						//printk("[bing]KEY_MENU \r\n");
					}
				}
          		  input_sync(st1232_ts->input_dev);
		}
//err:
	//printk("st1232_ts_update_pen_state\r\n");
}