]> rtime.felk.cvut.cz Git - lincan.git/blobdiff - lincan/src/unican.c
Changes, which should enable to handle more VME Unican cards under RT-Linux.
[lincan.git] / lincan / src / unican.c
index 4efabc874e98ef4be97510e1effc2f184fd08b93..f72bacc169eca68433c8f865ae82fa69df807abc 100644 (file)
@@ -558,10 +558,7 @@ void unican_irq_sync_activities(struct canchip_t *chip, struct msgobj_t *obj)
 /**
  * unican_irq_handler: - interrupt service routine
  * @irq: interrupt vector number, this value is system specific
- * @dev_id: driver private pointer registered at time of request_irq() call.
- *     The CAN driver uses this pointer to store relationship of interrupt
- *     to chip state structure - @struct canchip_t
- * @regs: system dependent value pointing to registers stored in exception frame
+ * @chip: pointer to chip state structure
  * 
  * Interrupt handler is activated when state of CAN controller chip changes,
  * there is message to be read or there is more space for new messages or
@@ -582,8 +579,13 @@ int unican_irq_handler(int irq, struct canchip_t *chip)
                return CANCHIP_IRQ_NONE;
        }
 
-       if (cl2_get_status(chipext, &status) == CL2_NO_REQUEST)
+       if (cl2_get_status(chipext, &status) == CL2_NO_REQUEST) {
+               /* Reenable interrupts generation, this has to be even there, 
+                * because irq_accept disables interrupts
+                */
+               cl2_gen_interrupt(chipext);
                return CANCHIP_IRQ_NONE;
+       }
 
        cl2_clear_interrupt(chipext);
 
@@ -606,12 +608,31 @@ int unican_irq_handler(int irq, struct canchip_t *chip)
                unican_read(chip, obj);
        }
 
+       /* Reenable interrupts generation */
        cl2_gen_interrupt(chipext);
 
        return CANCHIP_IRQ_HANDLED;
 }
 
 
+/**
+ * unican_irq_accept: - fast irq accept routine, blocks further interrupts
+ * @irq: interrupt vector number, this value is system specific
+ * @chip: pointer to chip state structure
+ * 
+ * This routine only accepts interrupt reception and stops further
+ * incoming interrupts, but does not handle situation causing interrupt.
+ * File: src/unican.c
+ */
+int unican_irq_accept(int irq, struct canchip_t *chip)
+{
+       sCAN_CARD *chipext = (sCAN_CARD *)chip->chip_data;
+
+       cl2_clear_interrupt(chipext);
+
+       return CANCHIP_IRQ_ACCEPTED;
+}
+
 /*void unican_do_tx_timeout(unsigned long data)
 {
        struct msgobj_t *obj=(struct msgobj_t *)data;
@@ -797,7 +818,7 @@ int unican_init_chip_data(struct candevice_t *candev, int chipnr)
        chip->chipspecops->start_chip=unican_start_chip;
        chip->chipspecops->stop_chip=unican_stop_chip;
        chip->chipspecops->irq_handler=unican_irq_handler;
-       chip->chipspecops->irq_accept=NULL;
+       chip->chipspecops->irq_accept=unican_irq_accept;
 
        return 0;
 }