Date: Mon, 12 Aug 2013 10:15:09 +0000 (UTC) From: Alexander Motin <mav@FreeBSD.org> To: src-committers@freebsd.org, svn-src-projects@freebsd.org Subject: svn commit: r254246 - projects/camlock/sys/cam Message-ID: <201308121015.r7CAF9KJ033143@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: mav Date: Mon Aug 12 10:15:09 2013 New Revision: 254246 URL: http://svnweb.freebsd.org/changeset/base/254246 Log: Revert r254226. We can't create per-SIM threads while holding SIM lock. Modified: projects/camlock/sys/cam/cam_sim.c projects/camlock/sys/cam/cam_sim.h projects/camlock/sys/cam/cam_xpt.c projects/camlock/sys/cam/cam_xpt.h Modified: projects/camlock/sys/cam/cam_sim.c ============================================================================== --- projects/camlock/sys/cam/cam_sim.c Mon Aug 12 10:11:10 2013 (r254245) +++ projects/camlock/sys/cam/cam_sim.c Mon Aug 12 10:15:09 2013 (r254246) @@ -33,7 +33,6 @@ __FBSDID("$FreeBSD$"); #include <sys/systm.h> #include <sys/malloc.h> #include <sys/kernel.h> -#include <sys/kthread.h> #include <sys/lock.h> #include <sys/mutex.h> @@ -66,7 +65,6 @@ cam_sim_alloc(sim_action_func sim_action int max_tagged_dev_transactions, struct cam_devq *queue) { struct cam_sim *sim; - int error; if (mtx == NULL) return (NULL); @@ -99,13 +97,7 @@ cam_sim_alloc(sim_action_func sim_action } mtx_init(&sim->sim_doneq_mtx, "CAM doneq", NULL, MTX_DEF); TAILQ_INIT(&sim->sim_doneq); - error = kproc_kthread_add(xpt_done_td, sim, &cam_proc, NULL, 0, 0, - "cam", "%s%d", sim_name, unit); - if (error != 0) { - mtx_destroy(&sim->sim_doneq_mtx); - free(sim, M_CAMSIM); - return (NULL); - } + return (sim); } @@ -122,12 +114,7 @@ cam_sim_free(struct cam_sim *sim, int fr } KASSERT(sim->refcount == 0, ("sim->refcount == 0")); - mtx_lock(&sim->sim_doneq_mtx); - sim->sim_doneq_flags |= CAM_SIM_DQ_EXIT; - wakeup(&sim->sim_doneq); - mtx_unlock(&sim->sim_doneq_mtx); - while (sim->sim_doneq_flags & CAM_SIM_DQ_EXIT) - msleep(&sim->sim_doneq_flags, sim->mtx, PRIBIO, "simfree2", 0); + if (free_devq) cam_simq_free(sim->devq); mtx_destroy(&sim->sim_doneq_mtx); Modified: projects/camlock/sys/cam/cam_sim.h ============================================================================== --- projects/camlock/sys/cam/cam_sim.h Mon Aug 12 10:11:10 2013 (r254245) +++ projects/camlock/sys/cam/cam_sim.h Mon Aug 12 10:15:09 2013 (r254246) @@ -97,7 +97,6 @@ struct cam_sim { TAILQ_HEAD(, ccb_hdr) sim_doneq; struct mtx sim_doneq_mtx; int sim_doneq_flags; -#define CAM_SIM_DQ_EXIT 0x01 #define CAM_SIM_DQ_ONQ 0x04 #define CAM_SIM_DQ_POLLED 0x08 #define CAM_SIM_DQ_BATCH 0x10 Modified: projects/camlock/sys/cam/cam_xpt.c ============================================================================== --- projects/camlock/sys/cam/cam_xpt.c Mon Aug 12 10:11:10 2013 (r254245) +++ projects/camlock/sys/cam/cam_xpt.c Mon Aug 12 10:15:09 2013 (r254246) @@ -156,7 +156,15 @@ TUNABLE_INT("kern.cam.boot_delay", &xsof SYSCTL_INT(_kern_cam, OID_AUTO, boot_delay, CTLFLAG_RDTUN, &xsoftc.boot_delay, 0, "Bus registration wait time"); -struct proc *cam_proc; +/* Queues for our software interrupt handler */ +typedef TAILQ_HEAD(cam_isrq, ccb_hdr) cam_isrq_t; +typedef TAILQ_HEAD(cam_simq, cam_sim) cam_simq_t; +static cam_simq_t cam_simq; +static struct mtx cam_simq_lock; + +/* Pointers to software interrupt handlers */ +static void *cambio_ih; + struct cam_periph *xpt_periph; static periph_init_t xpt_periph_init; @@ -241,6 +249,7 @@ static int xpt_schedule_dev(struct camq static xpt_devicefunc_t xptpassannouncefunc; static void xptaction(struct cam_sim *sim, union ccb *work_ccb); static void xptpoll(struct cam_sim *sim); +static void camisr(void *); static void camisr_runqueue(struct cam_sim *); static dev_match_ret xptbusmatch(struct dev_match_pattern *patterns, u_int num_patterns, struct cam_eb *bus); @@ -832,10 +841,12 @@ xpt_init(void *dummy) cam_status status; TAILQ_INIT(&xsoftc.xpt_busses); + TAILQ_INIT(&cam_simq); TAILQ_INIT(&xsoftc.ccb_scanq); STAILQ_INIT(&xsoftc.highpowerq); xsoftc.num_highpower = CAM_MAX_HIGHPOWER; + mtx_init(&cam_simq_lock, "CAM SIMQ lock", NULL, MTX_DEF); mtx_init(&xsoftc.xpt_lock, "XPT lock", NULL, MTX_DEF); mtx_init(&xsoftc.xpt_topo_lock, "XPT topology lock", NULL, MTX_DEF); xsoftc.xpt_taskq = taskqueue_create("CAM XPT task", M_WAITOK, @@ -893,6 +904,8 @@ xpt_init(void *dummy) path, NULL, 0, xpt_sim); xpt_free_path(path); mtx_unlock(&xsoftc.xpt_lock); + /* Install our software interrupt handlers */ + swi_add(NULL, "cambio", camisr, NULL, SWI_CAMBIO, INTR_MPSAFE, &cambio_ih); /* * Register a callback for when interrupts are enabled. */ @@ -4284,7 +4297,7 @@ void xpt_done(union ccb *done_ccb) { struct cam_sim *sim; - int run; + int first; CAM_DEBUG(done_ccb->ccb_h.path, CAM_DEBUG_TRACE, ("xpt_done\n")); if ((done_ccb->ccb_h.func_code & XPT_FC_QUEUED) != 0) { @@ -4299,13 +4312,16 @@ xpt_done(union ccb *done_ccb) done_ccb->ccb_h.pinfo.index = CAM_DONEQ_INDEX; if ((sim->sim_doneq_flags & (CAM_SIM_DQ_ONQ | CAM_SIM_DQ_POLLED | CAM_SIM_DQ_BATCH)) == 0) { + mtx_lock(&cam_simq_lock); + first = TAILQ_EMPTY(&cam_simq); + TAILQ_INSERT_TAIL(&cam_simq, sim, links); + mtx_unlock(&cam_simq_lock); sim->sim_doneq_flags |= CAM_SIM_DQ_ONQ; - run = 1; } else - run = 0; + first = 0; mtx_unlock(&sim->sim_doneq_mtx); - if (run) - wakeup(&sim->sim_doneq); + if (first) + swi_sched(cambio_ih, 0); } } @@ -4812,8 +4828,7 @@ xpt_config(void *arg) callout_reset(&xsoftc.boot_callout, hz * xsoftc.boot_delay / 1000, xpt_boot_delay, NULL); /* Fire up rescan thread. */ - if (kproc_kthread_add(xpt_scanner_thread, NULL, &cam_proc, NULL, 0, 0, - "cam", "scanner")) { + if (kproc_create(xpt_scanner_thread, NULL, NULL, 0, 0, "xpt_thrd")) { printf("xpt_config: failed to create rescan thread.\n"); } } @@ -5037,30 +5052,25 @@ xpt_path_mtx(struct cam_path *path) return (&path->device->device_mtx); } -void -xpt_done_td(void *arg) +static void +camisr(void *dummy) { - struct cam_sim *sim = arg; + cam_simq_t queue; + struct cam_sim *sim; - mtx_lock(&sim->sim_doneq_mtx); - while (1) { - if (TAILQ_EMPTY(&sim->sim_doneq)) { - if (sim->sim_doneq_flags & CAM_SIM_DQ_EXIT) { - mtx_unlock(&sim->sim_doneq_mtx); - CAM_SIM_LOCK(sim); - sim->sim_doneq_flags &= ~CAM_SIM_DQ_EXIT; - wakeup(&sim->sim_doneq_flags); - CAM_SIM_UNLOCK(sim); - kthread_exit(); - } - msleep(&sim->sim_doneq, &sim->sim_doneq_mtx, PRIBIO, - "-", 0); - continue; + mtx_lock(&cam_simq_lock); + TAILQ_INIT(&queue); + while (!TAILQ_EMPTY(&cam_simq)) { + TAILQ_CONCAT(&queue, &cam_simq, links); + mtx_unlock(&cam_simq_lock); + + while ((sim = TAILQ_FIRST(&queue)) != NULL) { + TAILQ_REMOVE(&queue, sim, links); + camisr_runqueue(sim); } - mtx_unlock(&sim->sim_doneq_mtx); - camisr_runqueue(sim); - mtx_lock(&sim->sim_doneq_mtx); + mtx_lock(&cam_simq_lock); } + mtx_unlock(&cam_simq_lock); } static void Modified: projects/camlock/sys/cam/cam_xpt.h ============================================================================== --- projects/camlock/sys/cam/cam_xpt.h Mon Aug 12 10:11:10 2013 (r254245) +++ projects/camlock/sys/cam/cam_xpt.h Mon Aug 12 10:15:09 2013 (r254246) @@ -62,7 +62,6 @@ struct async_node { SLIST_HEAD(async_list, async_node); SLIST_HEAD(periph_list, cam_periph); -extern struct proc *cam_proc; void xpt_action(union ccb *new_ccb); void xpt_action_default(union ccb *new_ccb); @@ -124,7 +123,6 @@ void xpt_copy_path(struct cam_path *ne struct cam_path *path); void xpt_release_path(struct cam_path *path); -void xpt_done_td(void *); #endif /* _KERNEL */
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201308121015.r7CAF9KJ033143>