Пример #1
0
static irqreturn_t irq_handler(int i, void *blah, struct pt_regs *regs)
{
	struct timeval tv;
	long deltv;
	int data;
	int signal;

	/* use the GPIO signal level */
	signal = gci->get(gci, gpio_in_pin);

	/* unmask the irq */
	irqchip->irq_unmask(irqdata);

	if (sense != -1) {
		/* get current time */
		do_gettimeofday(&tv);

		/* calc time since last interrupt in microseconds */
		deltv = tv.tv_sec-lasttv.tv_sec;
		if (tv.tv_sec < lasttv.tv_sec ||
		    (tv.tv_sec == lasttv.tv_sec &&
		     tv.tv_usec < lasttv.tv_usec)) {
			printk(KERN_WARNING LIRC_DRIVER_NAME
			       ": AIEEEE: your clock just jumped backwards\n");
			printk(KERN_WARNING LIRC_DRIVER_NAME
			       ": %d %d %lx %lx %lx %lx\n", signal, sense,
			       tv.tv_sec, lasttv.tv_sec,
			       tv.tv_usec, lasttv.tv_usec);
			data = PULSE_MASK;
		} else if (deltv > 15) {
			data = PULSE_MASK; /* really long time */
			if (!(signal^sense)) {
				/* sanity check */
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": AIEEEE: %d %d %lx %lx %lx %lx\n",
				       signal, sense, tv.tv_sec, lasttv.tv_sec,
				       tv.tv_usec, lasttv.tv_usec);
				/*
				 * detecting pulse while this
				 * MUST be a space!
				 */
				sense = sense ? 0 : 1;
			}
		} else {
			data = (int) (deltv*1000000 +
				      (tv.tv_usec - lasttv.tv_usec));
		}
		frbwrite(signal^sense ? data : (data|PULSE_BIT));
		lasttv = tv;
		wake_up_interruptible(&rbuf.wait_poll);
	}

	return IRQ_HANDLED;
}
Пример #2
0
static irqreturn_t irq_handler(int i, void *blah, struct pt_regs *regs)
{
	struct timeval tv;
	long deltv;
	int data;
	int signal;
	int index;

	for (index=0; index < INPUT_PIN_NUM ; index ++) {
		if (irq_num[index] == i)
			break;
	}
	
	/* use the GPIO signal level */
	signal = gpiochip->get(gpiochip, gpio_in_pin[index]);
	dprintk("irq_num %d signal %d  \n", i, signal);

	if (sense != -1) {
		/* get current time */
		do_gettimeofday(&tv);

		/* calc time since last interrupt in microseconds */
		deltv = tv.tv_sec-lasttv[index].tv_sec;
		if (tv.tv_sec < lasttv[index].tv_sec ||
		    (tv.tv_sec == lasttv[index].tv_sec &&
		     tv.tv_usec < lasttv[index].tv_usec)) {
			printk(KERN_WARNING LIRC_DRIVER_NAME
			       ": AIEEEE: your clock just jumped backwards\n");
			printk(KERN_WARNING LIRC_DRIVER_NAME
			       ": %d %d %lx %lx %lx %lx\n", signal, sense,
			       tv.tv_sec, lasttv[index].tv_sec,
			       tv.tv_usec, lasttv[index].tv_usec);
			data = PULSE_MASK;
		} else if (deltv > 15) {
			data = PULSE_MASK; /* really long time */
			if (!(signal^sense)) {
				/* sanity check */
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": AIEEEE: %d %d %lx %lx %lx %lx\n",
				       signal, sense, tv.tv_sec, lasttv[index].tv_sec,
				       tv.tv_usec, lasttv[index].tv_usec);
				/*
				 * detecting pulse while this
				 * MUST be a space!
				 */
				sense = sense ? 0 : 1;
			}
		} else {
			data = (int) (deltv*1000000 +
				      (tv.tv_usec - lasttv[index].tv_usec));
			dprintk("data  %d sense %d\n", data, sense);
		}
		if (ir_check_val == 0 ){
			if ((data > (length-50)) && (data < (length+50))){
				ir_check_val = (0x1 << (index*8));
				dprintk(" ir checked data  %d \n", data);
			}
		}
		if (index == 0)
			frbwrite(signal^sense ? data : (data|PULSE_BIT));
		
		lasttv[index] = tv;
		
		if (index == 0)
			wake_up_interruptible(&rbuf.wait_poll);
	}

	return IRQ_HANDLED;
}
Пример #3
0
static irqreturn_t serial_ir_irq_handler(int i, void *blah)
{
	ktime_t kt;
	int counter, dcd;
	u8 status;
	ktime_t delkt;
	unsigned int data;
	static int last_dcd = -1;

	if ((sinp(UART_IIR) & UART_IIR_NO_INT)) {
		/* not our interrupt */
		return IRQ_NONE;
	}

	counter = 0;
	do {
		counter++;
		status = sinp(UART_MSR);
		if (counter > RS_ISR_PASS_LIMIT) {
			dev_err(&serial_ir.pdev->dev, "Trapped in interrupt");
			break;
		}
		if ((status & hardware[type].signal_pin_change) &&
		    sense != -1) {
			/* get current time */
			kt = ktime_get();

			/*
			 * The driver needs to know if your receiver is
			 * active high or active low, or the space/pulse
			 * sense could be inverted.
			 */

			/* calc time since last interrupt in nanoseconds */
			dcd = (status & hardware[type].signal_pin) ? 1 : 0;

			if (dcd == last_dcd) {
				dev_err(&serial_ir.pdev->dev,
					"ignoring spike: %d %d %lldns %lldns\n",
					dcd, sense, ktime_to_ns(kt),
					ktime_to_ns(serial_ir.lastkt));
				continue;
			}

			delkt = ktime_sub(kt, serial_ir.lastkt);
			if (ktime_compare(delkt, ktime_set(15, 0)) > 0) {
				data = IR_MAX_DURATION; /* really long time */
				if (!(dcd ^ sense)) {
					/* sanity check */
					dev_err(&serial_ir.pdev->dev,
						"dcd unexpected: %d %d %lldns %lldns\n",
						dcd, sense, ktime_to_ns(kt),
						ktime_to_ns(serial_ir.lastkt));
					/*
					 * detecting pulse while this
					 * MUST be a space!
					 */
					sense = sense ? 0 : 1;
				}
			} else {
				data = ktime_to_ns(delkt);
			}
			frbwrite(data, !(dcd ^ sense));
			serial_ir.lastkt = kt;
			last_dcd = dcd;
		}
	} while (!(sinp(UART_IIR) & UART_IIR_NO_INT)); /* still pending ? */

	mod_timer(&serial_ir.timeout_timer,
		  jiffies + nsecs_to_jiffies(serial_ir.rcdev->timeout));

	ir_raw_event_handle(serial_ir.rcdev);

	return IRQ_HANDLED;
}
Пример #4
0
static irqreturn_t irq_handler(int i, void *blah, struct pt_regs *regs)
#endif
{
	struct timeval tv;
	int status,counter,dcd;
	long deltv;
	lirc_t data;
	
	if((sinp(UART_IIR) & UART_IIR_NO_INT))
	{
		/* not our interrupt */
		return IRQ_RETVAL(IRQ_NONE);
	}
	
	counter=0;
	do{
		counter++;
		status=sinp(UART_MSR);
		if(counter>RS_ISR_PASS_LIMIT)
		{
			printk(KERN_WARNING LIRC_DRIVER_NAME ": AIEEEE: "
			       "We're caught!\n");
			break;
		}
		if((status&hardware[type].signal_pin_change) && sense!=-1)
		{
			/* get current time */
			do_gettimeofday(&tv);
			
			/* New mode, written by Trent Piepho 
			   <*****@*****.**>. */
			
			/* The old format was not very portable.
			   We now use the type lirc_t to pass pulses
			   and spaces to user space.
			   
			   If PULSE_BIT is set a pulse has been
			   received, otherwise a space has been
			   received.  The driver needs to know if your
			   receiver is active high or active low, or
			   the space/pulse sense could be
			   inverted. The bits denoted by PULSE_MASK are
			   the length in microseconds. Lengths greater
			   than or equal to 16 seconds are clamped to
			   PULSE_MASK.  All other bits are unused.
			   This is a much simpler interface for user
			   programs, as well as eliminating "out of
			   phase" errors with space/pulse
			   autodetection. */

			/* calculate time since last interrupt in
			   microseconds */
			dcd=(status & hardware[type].signal_pin) ? 1:0;
			
			deltv=tv.tv_sec-lasttv.tv_sec;
			if(tv.tv_sec<lasttv.tv_sec ||
			   (tv.tv_sec==lasttv.tv_sec &&
			    tv.tv_usec<lasttv.tv_usec))
			{
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": AIEEEE: your clock just jumped "
				       "backwards\n");
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": %d %d %lx %lx %lx %lx\n",
				       dcd,sense,
				       tv.tv_sec,lasttv.tv_sec,
				       tv.tv_usec,lasttv.tv_usec);
				data=PULSE_MASK;
			}
			else if(deltv>15) 
			{
				data=PULSE_MASK; /* really long time */
				if(!(dcd^sense)) /* sanity check */
				{
					printk(KERN_WARNING LIRC_DRIVER_NAME
					       "AIEEEE: %d %d %lx %lx %lx %lx\n",
					       dcd,sense,
					       tv.tv_sec,lasttv.tv_sec,
					       tv.tv_usec,lasttv.tv_usec);
				        /* detecting pulse while this
					   MUST be a space! */
				        sense=sense ? 0:1;
				}
			}
			else
			{
				data=(lirc_t) (deltv*1000000+
					       tv.tv_usec-
					       lasttv.tv_usec);
			}
			frbwrite(dcd^sense ? data : (data|PULSE_BIT));
			lasttv=tv;
			wake_up_interruptible(&rbuf.wait_poll);
		}
	} while(!(sinp(UART_IIR) & UART_IIR_NO_INT)); /* still pending ? */
	return IRQ_RETVAL(IRQ_HANDLED);
}
Пример #5
0
void irq_handler(int i, void *blah, struct pt_regs *regs)
{
	static struct timeval tv;
	int status,counter,dcd;
	long deltv;
	lirc_t data;
	unsigned long flags;

#ifndef LIRC_PORT
	save_flags(flags);cli();
	data= (lirc_t) (fast_tv.tv_sec*1000000+ fast_tv.tv_usec);
	pin_status = (pin_status + 1) & 0x1;
	if (data > 100000 && pin_status == 0) {/* 1/2 second fixup if broken */
		pin_status = 1;
		printk("F");
	}
	restore_flags(flags);
#endif

	counter=0;
	do{
#if DAVIDM
		counter++;
#ifndef LIRC_PORT
		status=LIRC_SIGNAL_PIN_CHANGE | (pin_status ? LIRC_SIGNAL_PIN : 0);
#else
		status=sinp(UART_MSR);
#endif
		if(counter>RS_ISR_PASS_LIMIT)
		{
			printk(KERN_WARNING LIRC_DRIVER_NAME ": AIEEEE: "
			       "We're caught!\n");
			break;
		}
		if((status&LIRC_SIGNAL_PIN_CHANGE) && sense!=-1)
#endif /* DAVIDM */
		{
#if DAVIDM
			/* get current time */
			do_gettimeofday(&tv);
#endif
			
			/* New mode, written by Trent Piepho 
			   <*****@*****.**>. */
			
			/* The old format was not very portable.
			   We now use the type lirc_t to pass pulses
			   and spaces to user space.
			   
			   If PULSE_BIT is set a pulse has been
			   received, otherwise a space has been
			   received.  The driver needs to know if your
			   receiver is active high or active low, or
			   the space/pulse sense could be
			   inverted. The bits denoted by PULSE_MASK are
			   the length in microseconds. Lengths greater
			   than or equal to 16 seconds are clamped to
			   PULSE_MASK.  All other bits are unused.
			   This is a much simpler interface for user
			   programs, as well as eliminating "out of
			   phase" errors with space/pulse
			   autodetection. */

			/* calculate time since last interrupt in
			   microseconds */
#if DAVIDM
			dcd=(status & LIRC_SIGNAL_PIN) ? 1:0;

			deltv=tv.tv_sec-lasttv.tv_sec;
#else
			dcd=pin_status;

			deltv=fast_tv.tv_sec;
#endif
			if(deltv>15) 
			{
#ifdef DEBUG
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": AIEEEE: %d %d %lx %lx %lx %lx\n",
				       dcd,sense,
				       tv.tv_sec,lasttv.tv_sec,
				       tv.tv_usec,lasttv.tv_usec);
#endif
				data=PULSE_MASK; /* really long time */
				if(!(dcd^sense)) /* sanity check */
				{
				        /* detecting pulse while this
					   MUST be a space! */
				        sense=sense ? 0:1;
				}
			}
			else
			{
#ifdef DAVIDM
				data=(lirc_t) (deltv*1000000+ tv.tv_usec- lasttv.tv_usec);
#else
				// data=(lirc_t) (fast_tv.tv_sec*1000000+ fast_tv.tv_usec);
#endif
			}
#if DAVIDM
			if(tv.tv_sec<lasttv.tv_sec ||
			   (tv.tv_sec==lasttv.tv_sec &&
			    tv.tv_usec<lasttv.tv_usec))
			{
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": AIEEEE: your clock just jumped "
				       "backwards\n");
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       "%d %d %lx %lx %lx %lx\n",
				       dcd,sense,
				       tv.tv_sec,lasttv.tv_sec,
				       tv.tv_usec,lasttv.tv_usec);
				data=PULSE_MASK;
			}
#endif
			frbwrite(dcd^sense ? data : (data|PULSE_BIT));
#if DAVIDM
			lasttv=tv;
#else
			fast_tv.tv_sec = fast_tv.tv_usec = 0;
#endif
			wake_up_interruptible(&lirc_wait_in);
		}
	}
#ifndef CONFIG_COLDFIRE
	while(!(sinp(UART_IIR) & UART_IIR_NO_INT)); /* still pending ? */
#else
	while (0);
#endif

#ifndef LIRC_PORT
#ifndef LIRC_PORT
	* (volatile unsigned long *) (MCF_MBAR + MCFSIM_ICR1) = 0xe0000000;
#endif
#endif
}
Пример #6
0
static irqreturn_t irq_handler(int i, void *blah, struct pt_regs *regs)
#endif
{
	u32 reg;
	int negate = 0;
	struct timeval tv;
	int counter, dcd;
	long deltv;
	int data;
	static int last_dcd = -1;
	static int count = 0;
	count++;
	/* First thing first - flip the bit */
	reg = readl(GPIO_IN_POL(19));
	if (reg & (1<< 19)) {reg &= ~(1<<19);negate=1;}
	else reg |= (1<< 19);
	writel(reg, GPIO_IN_POL(19));
	/* Now read the actual data */
	counter = 0;
	do {
		counter++;
		if (counter > RS_ISR_PASS_LIMIT) {
			printk(KERN_WARNING LIRC_DRIVER_NAME ": AIEEEE: "
			       "We're caught!\n");
			break;
		}
		if (1 /*(status & hardware[type].signal_pin_change) && sense != -1*/) {
			/* get current time */
			do_gettimeofday(&tv);

			/* New mode, written by Trent Piepho
			   <*****@*****.**>. */

			/*
			 * The old format was not very portable.
			 * We now use an int to pass pulses
			 * and spaces to user space.
			 *
			 * If PULSE_BIT is set a pulse has been
			 * received, otherwise a space has been
			 * received.  The driver needs to know if your
			 * receiver is active high or active low, or
			 * the space/pulse sense could be
			 * inverted. The bits denoted by PULSE_MASK are
			 * the length in microseconds. Lengths greater
			 * than or equal to 16 seconds are clamped to
			 * PULSE_MASK.  All other bits are unused.
			 * This is a much simpler interface for user
			 * programs, as well as eliminating "out of
			 * phase" errors with space/pulse
			 * autodetection.
			 */

			/* calc time since last interrupt in microseconds */
			dcd = (negate /*reg & (1<< 19)*/) /*//(status & hardware[type].signal_pin)*/ ? 0 : 1;

			if (dcd == last_dcd) {
				printk(KERN_WARNING LIRC_DRIVER_NAME
				": ignoring spike: %d %d %lx %lx %lx %lx\n",
				dcd, sense,
				tv.tv_sec, lasttv.tv_sec,
				tv.tv_usec, lasttv.tv_usec);
				continue;
			}

			deltv = tv.tv_sec-lasttv.tv_sec;
			if (tv.tv_sec < lasttv.tv_sec ||
			    (tv.tv_sec == lasttv.tv_sec &&
			     tv.tv_usec < lasttv.tv_usec)) {
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": AIEEEE: your clock just jumped "
				       "backwards\n");
				printk(KERN_WARNING LIRC_DRIVER_NAME
				       ": %d %d %lx %lx %lx %lx\n",
				       dcd, sense,
				       tv.tv_sec, lasttv.tv_sec,
				       tv.tv_usec, lasttv.tv_usec);
				data = PULSE_MASK;
			} else if (deltv > 15) {
				data = PULSE_MASK; /* really long time */
				if (!(dcd^sense)) {
					/* sanity check */
					printk ("ERROR\n");
					printk(KERN_WARNING LIRC_DRIVER_NAME
					       ": AIEEEE: "
					       "%d %d %lx %lx %lx %lx\n",
					       dcd, sense,
					       tv.tv_sec, lasttv.tv_sec,
					       tv.tv_usec, lasttv.tv_usec);
					/*
					 * detecting pulse while this
					 * MUST be a space!
					 */
					sense = sense ? 0 : 1;
				}
			} else
				data = (int) (deltv*1000000 +
					       tv.tv_usec -
					       lasttv.tv_usec);
			frbwrite(dcd^sense ? data : (data|PULSE_BIT));
#if 0 // Original code below - WTF ??!!
			lasttv = tv;
#else
			memcpy (&lasttv, &tv, sizeof(struct timeval));
#endif
			last_dcd = dcd;

			wake_up_interruptible(&rbuf.wait_poll);
		}
	} while (0);//!(sinp(UART_IIR) & UART_IIR_NO_INT)); /* still pending ? */
	return IRQ_HANDLED;
}