Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 1 Feb 2009 20:01:05 +0100
From:      Hans Petter Selasky <hselasky@c2i.net>
To:        freebsd-usb@freebsd.org
Cc:        thompsa@freebsd.org
Subject:   Re: USB2 patches
Message-ID:  <200902012001.06914.hselasky@c2i.net>
In-Reply-To: <200902011938.48670.hselasky@c2i.net>
References:  <200902011220.18745.hselasky@c2i.net> <20090201.112756.1320088159.imp@bsdimp.com> <200902011938.48670.hselasky@c2i.net>

next in thread | previous in thread | raw e-mail | index | archive | help
Hi Andrew,

Regarding using taskqueues.

Yes - USB2 can use taskqueues, but I would very much like to have the original 
queueing mechanism intact.

How about:

struct task *
tasqueue_enqueue_pair(struct taskqueue *queue, struct task *t0, struct task 
*t1);

Which does something similar to this:

void   *
usb2_proc_msignal(struct usb2_process *up, void *_pm0, void *_pm1)
{
        struct usb2_proc_msg *pm0 = _pm0;
        struct usb2_proc_msg *pm1 = _pm1;
        struct usb2_proc_msg *pm2;
        uint32_t d;
        uint8_t t;

        mtx_assert(up->up_mtx, MA_OWNED);

        t = 0;

        if (pm0->pm_qentry.tqe_prev) {
                t |= 1;
        }
        if (pm1->pm_qentry.tqe_prev) {
                t |= 2;
        }
        if (t == 0) {
                /*
                 * No entries are queued. Queue "pm0" and use the existing
                 * message number.
                 */
                pm2 = pm0;
        } else if (t == 1) {
                /* Check if we need to increment the message number. */
                if (pm0->pm_num == up->up_msg_num) {
                        up->up_msg_num++;
                }
                pm2 = pm1;
        } else if (t == 2) {
                /* Check if we need to increment the message number. */
                if (pm1->pm_num == up->up_msg_num) {
                        up->up_msg_num++;
                }
                pm2 = pm0;
        } else if (t == 3) {
                /*
                 * Both entries are queued. Re-queue the entry closest to
                 * the end.
                 */
                d = (pm1->pm_num - pm0->pm_num);

                /* Check sign after subtraction */
                if (d & 0x80000000) {
                        pm2 = pm0;
                } else {
                        pm2 = pm1;
                }

                TAILQ_REMOVE(&up->up_qhead, pm2, pm_qentry);
        } else {
                pm2 = NULL;             /* panic - should not happen */
        }

        DPRINTF(" t=%u, num=%u\n", t, up->up_msg_num);

        /* Put message last on queue */

        pm2->pm_num = up->up_msg_num;
        TAILQ_INSERT_TAIL(&up->up_qhead, pm2, pm_qentry);

        /* Check if we need to wakeup the USB process. */

        if (up->up_msleep) {
                up->up_msleep = 0;      /* save "cv_signal()" calls */
                usb2_cv_signal(&up->up_cv);
        }
        return (pm2);
}

--HPS



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