Message ID | 1356142552-13453-13-git-send-email-scottwood@freescale.com |
---|---|
State | New |
Headers | show |
On 22.12.2012, at 03:15, Scott Wood wrote: > Search the queue more efficiently by first looking for a non-zero word, > and then using the common bit-searching function to find the bit within > the word. It would be even nicer if bitops_ffsl() could be hooked up > to the compiler intrinsic so that bit-searching instructions could be > used, but that's another matter. > > Signed-off-by: Scott Wood <scottwood@freescale.com> What we really want is a bitmap wide ffs() bipops helper function that returns the first set bit in a bitmap and can optimize the hell out of that operation inside of itself. I don't think this belongs to the OpenPIC code. Alex > --- > hw/openpic.c | 28 +++++++++++++++++++++------- > 1 file changed, 21 insertions(+), 7 deletions(-) > > diff --git a/hw/openpic.c b/hw/openpic.c > index f2ac286..5accff5 100644 > --- a/hw/openpic.c > +++ b/hw/openpic.c > @@ -270,21 +270,35 @@ static inline int IRQ_testbit(IRQ_queue_t *q, int n_IRQ) > > static void IRQ_check(OpenPICState *opp, IRQ_queue_t *q) > { > - int next, i; > + int next, word, irq, base; > int priority; > > next = -1; > priority = -1; > - for (i = 0; i < opp->max_irq; i++) { > - if (IRQ_testbit(q, i)) { > + > + for (word = 0, base = 0; word < ARRAY_SIZE(q->queue); > + word++, base += BITS_PER_LONG) { > + unsigned long map = q->queue[word]; > + > + if (!map) { > + continue; > + } > + > + while (map) { > + int offset = bitops_ffsl(map); > + irq = base + offset; > + map &= ~(1UL << offset); > + > DPRINTF("IRQ_check: irq %d set ivpr_pr=%d pr=%d\n", > - i, IVPR_PRIORITY(opp->src[i].ivpr), priority); > - if (IVPR_PRIORITY(opp->src[i].ivpr) > priority) { > - next = i; > - priority = IVPR_PRIORITY(opp->src[i].ivpr); > + irq, IVPR_PRIORITY(opp->src[irq].ivpr), priority); > + > + if (IVPR_PRIORITY(opp->src[irq].ivpr) > priority) { > + next = irq; > + priority = IVPR_PRIORITY(opp->src[irq].ivpr); > } > } > } > + > q->next = next; > q->priority = priority; > } > -- > 1.7.9.5 > >
diff --git a/hw/openpic.c b/hw/openpic.c index f2ac286..5accff5 100644 --- a/hw/openpic.c +++ b/hw/openpic.c @@ -270,21 +270,35 @@ static inline int IRQ_testbit(IRQ_queue_t *q, int n_IRQ) static void IRQ_check(OpenPICState *opp, IRQ_queue_t *q) { - int next, i; + int next, word, irq, base; int priority; next = -1; priority = -1; - for (i = 0; i < opp->max_irq; i++) { - if (IRQ_testbit(q, i)) { + + for (word = 0, base = 0; word < ARRAY_SIZE(q->queue); + word++, base += BITS_PER_LONG) { + unsigned long map = q->queue[word]; + + if (!map) { + continue; + } + + while (map) { + int offset = bitops_ffsl(map); + irq = base + offset; + map &= ~(1UL << offset); + DPRINTF("IRQ_check: irq %d set ivpr_pr=%d pr=%d\n", - i, IVPR_PRIORITY(opp->src[i].ivpr), priority); - if (IVPR_PRIORITY(opp->src[i].ivpr) > priority) { - next = i; - priority = IVPR_PRIORITY(opp->src[i].ivpr); + irq, IVPR_PRIORITY(opp->src[irq].ivpr), priority); + + if (IVPR_PRIORITY(opp->src[irq].ivpr) > priority) { + next = irq; + priority = IVPR_PRIORITY(opp->src[irq].ivpr); } } } + q->next = next; q->priority = priority; }
Search the queue more efficiently by first looking for a non-zero word, and then using the common bit-searching function to find the bit within the word. It would be even nicer if bitops_ffsl() could be hooked up to the compiler intrinsic so that bit-searching instructions could be used, but that's another matter. Signed-off-by: Scott Wood <scottwood@freescale.com> --- hw/openpic.c | 28 +++++++++++++++++++++------- 1 file changed, 21 insertions(+), 7 deletions(-)