From owner-freebsd-scsi@FreeBSD.ORG Thu Sep 23 14:30:42 2010 Return-Path: Delivered-To: freebsd-scsi@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id 039E41065693 for ; Thu, 23 Sep 2010 14:30:42 +0000 (UTC) (envelope-from mjohnston@sandvine.com) Received: from mail1.sandvine.com (Mail1.sandvine.com [64.7.137.134]) by mx1.freebsd.org (Postfix) with ESMTP id 998538FC1F for ; Thu, 23 Sep 2010 14:30:41 +0000 (UTC) Received: from WTL-EXCH-2.sandvine.com ([fe80::8959:ede3:2dbe:c1b]) by wtl-exch-1.sandvine.com ([fe80::f523:8e57:71d7:5206%14]) with mapi; Thu, 23 Sep 2010 10:19:54 -0400 From: Mark Johnston To: "freebsd-scsi@freebsd.org" Thread-Topic: [PATCH] trigger cam rescans in aac Thread-Index: ActbJ+sd+JKJPIh2QYClvJChBIisVAAAmR0A Date: Thu, 23 Sep 2010 14:19:47 +0000 Message-ID: <649630C24D5E884F85DD13645FE903A7ACA7@wtl-exch-2.sandvine.com> Accept-Language: en-US Content-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: x-cr-puzzleid: {C9EA6ECB-B36C-40D7-8E69-DD753925B556} x-cr-hashedpuzzle: hCc= AIVR BaGD BkGe CUuX Ddbi DxBp EDwo EjTh FL63 FYvy Fm/d GL2D GfU2 HWtE IIPu; 1; ZgByAGUAZQBiAHMAZAAtAHMAYwBzAGkAQABmAHIAZQBlAGIAcwBkAC4AbwByAGcA; Sosha1_v1; 7; {C9EA6ECB-B36C-40D7-8E69-DD753925B556}; bQBqAG8AaABuAHMAdABvAG4AQABzAGEAbgBkAHYAaQBuAGUALgBjAG8AbQA=; Thu, 23 Sep 2010 14:19:47 GMT; WwBQAEEAVABDAEgAXQAgAHQAcgBpAGcAZwBlAHIAIABjAGEAbQAgAHIAZQBzAGMAYQBuAHMAIABpAG4AIABhAGEAYwA= Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Subject: [PATCH] trigger cam rescans in aac X-BeenThere: freebsd-scsi@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: SCSI subsystem List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 23 Sep 2010 14:30:42 -0000 Hi, Previously, the aac driver did not handle enclosure management AIFs, which were raised during hot-swap events. Now such events trigger cam rescans, as is done in the mps driver. Any comments or suggestions would be appreciated. Thanks, -Mark --- tmp/aac/aac.c 2010-09-16 13:24:53.000000000 -0400 +++ aac.c 2010-09-21 13:40:51.000000000 -0400 @@ -3209,6 +3209,7 @@ aac_handle_aif(struct aac_softc *sc, str struct aac_mntinforesp *mir; int next, current, found; int count =3D 0, added =3D 0, i =3D 0; + uint32_t channel; =20 fwprintf(sc, HBA_FLAGS_DBG_FUNCTION_ENTRY_B, ""); =20 @@ -3316,7 +3317,25 @@ aac_handle_aif(struct aac_softc *sc, str } =20 break; - + case AifEnEnclosureManagement: + switch (aif->data.EN.data.EEE.eventType) { + case AIF_EM_DRIVE_INSERTION: + case AIF_EM_DRIVE_REMOVAL: + channel =3D aif->data.EN.data.EEE.unitID; + if (sc->cam_rescan_cb !=3D NULL) + sc->cam_rescan_cb(sc,=20 + (channel >> 24) & 0xF, + (channel & 0xFFFF)); + break; + } + break; + case AifEnAddJBOD: + case AifEnDeleteJBOD: + channel =3D aif->data.EN.data.ECE.container; + if (sc->cam_rescan_cb !=3D NULL) + sc->cam_rescan_cb(sc, (channel >> 24) & 0xF, + AAC_CAM_TARGET_WILDCARD); + break; default: break; } --- tmp/aac/aac_cam.c 2010-09-16 13:24:53.000000000 -0400 +++ aac_cam.c 2010-09-21 13:40:21.000000000 -0400 @@ -37,12 +37,15 @@ __FBSDID("$FreeBSD: src/sys/dev/aac/aac_ #include #include #include +#include #include #include +#include =20 #include #include #include +#include #include #include #include @@ -76,6 +79,8 @@ static int aac_cam_detach(device_t dev); static void aac_cam_action(struct cam_sim *, union ccb *); static void aac_cam_poll(struct cam_sim *); static void aac_cam_complete(struct aac_command *); +static void aac_cam_rescan(struct aac_softc *sc, uint32_t channel, + uint32_t target_id); static u_int32_t aac_cam_reset_bus(struct cam_sim *, union ccb *); static u_int32_t aac_cam_abort_ccb(struct cam_sim *, union ccb *); static u_int32_t aac_cam_term_io(struct cam_sim *, union ccb *); @@ -101,6 +106,39 @@ MODULE_DEPEND(aacp, cam, 1, 1, 1); MALLOC_DEFINE(M_AACCAM, "aaccam", "AAC CAM info"); =20 static void +aac_cam_rescan(struct aac_softc *sc, uint32_t channel, uint32_t target_id) +{ + union ccb *ccb; + struct aac_sim *sim; + struct aac_cam *camsc; + + TAILQ_FOREACH(sim, &sc->aac_sim_tqh, sim_link) { + camsc =3D sim->aac_cam; + if (camsc =3D=3D NULL || camsc->inf =3D=3D NULL || + camsc->inf->BusNumber !=3D channel) + continue; + + ccb =3D xpt_alloc_ccb_nowait(); + if (ccb =3D=3D NULL) { + device_printf(sc->aac_dev, + "Cannot allocate ccb for bus rescan.\n"); + return; + } + + if (xpt_create_path(&ccb->ccb_h.path, xpt_periph, + cam_sim_path(camsc->sim), + target_id, CAM_LUN_WILDCARD) !=3D CAM_REQ_CMP) { + xpt_free_ccb(ccb); + device_printf(sc->aac_dev, + "Cannot create path for bus rescan.\n"); + return; + } + xpt_rescan(ccb); + break; + } +} + +static void aac_cam_event(struct aac_softc *sc, struct aac_event *event, void *arg) { union ccb *ccb; @@ -141,6 +179,7 @@ aac_cam_detach(device_t dev) =20 camsc =3D (struct aac_cam *)device_get_softc(dev); sc =3D camsc->inf->aac_sc; + camsc->inf->aac_cam =3D NULL; =20 mtx_lock(&sc->aac_io_lock); =20 @@ -149,6 +188,8 @@ aac_cam_detach(device_t dev) xpt_bus_deregister(cam_sim_path(camsc->sim)); cam_sim_free(camsc->sim, /*free_devq*/TRUE); =20 + sc->cam_rescan_cb =3D NULL; + mtx_unlock(&sc->aac_io_lock); =20 return (0); @@ -171,6 +212,7 @@ aac_cam_attach(device_t dev) camsc =3D (struct aac_cam *)device_get_softc(dev); inf =3D (struct aac_sim *)device_get_ivars(dev); camsc->inf =3D inf; + camsc->inf->aac_cam =3D camsc; =20 devq =3D cam_simq_alloc(inf->TargetsPerBus); if (devq =3D=3D NULL) @@ -198,6 +240,7 @@ aac_cam_attach(device_t dev) mtx_unlock(&inf->aac_sc->aac_io_lock); return (EIO); } + inf->aac_sc->cam_rescan_cb =3D aac_cam_rescan; mtx_unlock(&inf->aac_sc->aac_io_lock); =20 camsc->sim =3D sim; @@ -611,4 +654,3 @@ aac_cam_term_io(struct cam_sim *sim, uni { return (CAM_UA_TERMIO); } - --- tmp/aac/aacvar.h 2010-09-16 13:24:53.000000000 -0400 +++ aacvar.h 2010-09-21 13:41:14.000000000 -0400 @@ -120,6 +120,7 @@ struct aac_sim int BusNumber; int InitiatorBusId; struct aac_softc *aac_sc; + struct aac_cam *aac_cam; TAILQ_ENTRY(aac_sim) sim_link; }; =20 @@ -383,6 +384,9 @@ struct aac_softc=20 struct selinfo rcv_select; struct proc *aifthread; int aifflags; +#define AAC_CAM_TARGET_WILDCARD ~0 + void (*cam_rescan_cb)(struct aac_softc *, uint32_t, + uint32_t); #define AAC_AIFFLAGS_RUNNING (1 << 0) #define AAC_AIFFLAGS_AIF (1 << 1) #define AAC_AIFFLAGS_EXIT (1 << 2) --- tmp/aac/aacreg.h 2010-09-16 13:24:53.000000000 -0400 +++ aacreg.h 2010-09-20 14:27:52.000000000 -0400 @@ -885,6 +885,8 @@ typedef enum { AifEnBatteryNeedsRecond, /* The battery needs reconditioning */ AifEnClusterEvent, /* Some cluster event */ AifEnDiskSetEvent, /* A disk set event occured. */ + AifEnAddJBOD=3D31, /* A new JBOD type drive was created. */ + AifEnDeleteJBOD, /* A JBOD type drive was deleted. */ AifDriverNotifyStart=3D199, /* Notifies for host driver go here */ /* Host driver notifications start here */ AifDenMorphComplete, /* A morph operation completed */ @@ -922,6 +924,11 @@ struct aac_AifEnsEnclosureEvent { u_int32_t eventType; /* event type */ } __packed; =20 +typedef enum { + AIF_EM_DRIVE_INSERTION=3D31, + AIF_EM_DRIVE_REMOVAL +} aac_AifEMEventType; + struct aac_AifEnsBatteryEvent { AAC_NVBATT_TRANSITION transition_type; /* eg from low to ok */ AAC_NVBATTSTATUS current_state; /* current batt state */