Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 8 Jan 1997 00:19:40 -0700 (MST)
From:      Nate Williams <nate@mt.sri.com>
To:        current@freebsd.org
Subject:   Interrupt masks???
Message-ID:  <199701080719.AAA29775@rocky.mt.sri.com>

next in thread | raw e-mail | index | archive | help
What are their purpose?  I'm trying to determine how exactly one
'registers' and enables interrupts in FreeBSD.

For context, the prototype for register_intr/unregister_intr are:

int register_intr(irq, dev_id, flags, handler, imask, unit)
  irq - integer number ( 0 - 16)
  dev_id - 'counter' it gets register to in the system counters (??)
  flags - normal or fast (serial) interrupts
  handler - function called when an interrupt occurs (takes in int)
  imask - ????
  unit - int parameter to handler function (XXX - used for pointers)

Returns successful/unsuccessful status.

int unregister_intr(irq, handler)
  irq - integer number ( 0 - 16)
  handler - function called when an interrupt occurs (takes in int)

Returns successful/unsuccessful status.

Plus we have:

int update_intr_masks(void)

Returns ???

My guesses to what things do:

INTREN()  - Enables interrupts for that device?  (A device can generate
            interrupts whether or not we enable, true?)

INTRDIS() - Disable interrupts?

ffs(irq) == (1 << irq)

To 'register' an interrupt for use it appears 3 steps are necessary:

INTRMASK(*imask, (1 << irq));
register_intr(irq, id, 0, intr_handler, imask, handler_arg);
INTREN(1 << irq);

* Although the PCI code switches ignores the first step and calls
  update_intr_masks(), which I can't tell what it does.

It appears that for 'unregistering' an interrupt we then do:
INTRDIS(1 << irq);
unregister_intr(irq, intr_handler);
INTRUNMASK(*imask, (1 << irq));

* Again, PCI is different in that they ignore the INTRUNMASK but again
  call update_intr_masks().

What's the purpose of the imask parameter in INTRMASK(), INTRUNMASK() and
register_intr()?  It appears to be on a per/IRQ basis, and we
set it to all ones at unregister_intr() time.  Does this have to do with
the whole spl*() stuff?

Other questions:
- Can an interrupt be generated if it's not enabled via INTREN()?  If
  so, how does it show up?



Nate
ps. Does someone want to review this patch for me?  The code uses
INTRMASK above, so why not INTRUNMASK below?

Index: pcibus.c
===================================================================
RCS file: /home/CVS/src/sys/i386/isa/pcibus.c,v
retrieving revision 1.27
diff -u -r1.27 pcibus.c
--- pcibus.c    1996/10/30 22:38:55     1.27
+++ pcibus.c    1997/01/08 06:25:35
@@ -519,7 +519,7 @@
        if (! (*maskptr & mask))
                return (-1);
 
-       *maskptr &= ~mask;
+       INTRUNMASK(*maskptr,mask);
        update_intr_masks();
 
        return (0);




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199701080719.AAA29775>