diff options
| author | Matt Jacob <mjacob@FreeBSD.org> | 2006-04-21 18:30:01 +0000 |
|---|---|---|
| committer | Matt Jacob <mjacob@FreeBSD.org> | 2006-04-21 18:30:01 +0000 |
| commit | 9cd7268e5a65afd2647466562c433ad193e54f24 (patch) | |
| tree | d3b3f19e96f6129f2561de62e8c2131359d8ae0e /sys/dev | |
| parent | b4d7b9794bdf47f2f8f30e736951ac9e5368f634 (diff) | |
Notes
Diffstat (limited to 'sys/dev')
| -rw-r--r-- | sys/dev/isp/isp.c | 149 | ||||
| -rw-r--r-- | sys/dev/isp/isp_freebsd.c | 238 | ||||
| -rw-r--r-- | sys/dev/isp/isp_freebsd.h | 33 | ||||
| -rw-r--r-- | sys/dev/isp/isp_ioctl.h | 2 | ||||
| -rw-r--r-- | sys/dev/isp/isp_pci.c | 597 | ||||
| -rw-r--r-- | sys/dev/isp/isp_sbus.c | 46 | ||||
| -rw-r--r-- | sys/dev/isp/isp_target.c | 56 | ||||
| -rw-r--r-- | sys/dev/isp/isp_target.h | 6 | ||||
| -rw-r--r-- | sys/dev/isp/isp_tpublic.h | 273 | ||||
| -rw-r--r-- | sys/dev/isp/ispmbox.h | 4 |
10 files changed, 850 insertions, 554 deletions
diff --git a/sys/dev/isp/isp.c b/sys/dev/isp/isp.c index 219c62c10f957..8d28afcf2baa5 100644 --- a/sys/dev/isp/isp.c +++ b/sys/dev/isp/isp.c @@ -114,40 +114,40 @@ static const char bun[] = /* * Local function prototypes. */ -static int isp_parse_async(struct ispsoftc *, uint16_t); -static int isp_handle_other_response(struct ispsoftc *, int, isphdr_t *, +static int isp_parse_async(ispsoftc_t *, uint16_t); +static int isp_handle_other_response(ispsoftc_t *, int, isphdr_t *, uint16_t *); static void -isp_parse_status(struct ispsoftc *, ispstatusreq_t *, XS_T *); -static void isp_fastpost_complete(struct ispsoftc *, uint16_t); -static int isp_mbox_continue(struct ispsoftc *); -static void isp_scsi_init(struct ispsoftc *); -static void isp_scsi_channel_init(struct ispsoftc *, int); -static void isp_fibre_init(struct ispsoftc *); -static void isp_mark_getpdb_all(struct ispsoftc *); -static int isp_getmap(struct ispsoftc *, fcpos_map_t *); -static int isp_getpdb(struct ispsoftc *, int, isp_pdb_t *); -static uint64_t isp_get_portname(struct ispsoftc *, int, int); -static int isp_fclink_test(struct ispsoftc *, int); +isp_parse_status(ispsoftc_t *, ispstatusreq_t *, XS_T *); +static void isp_fastpost_complete(ispsoftc_t *, uint16_t); +static int isp_mbox_continue(ispsoftc_t *); +static void isp_scsi_init(ispsoftc_t *); +static void isp_scsi_channel_init(ispsoftc_t *, int); +static void isp_fibre_init(ispsoftc_t *); +static void isp_mark_getpdb_all(ispsoftc_t *); +static int isp_getmap(ispsoftc_t *, fcpos_map_t *); +static int isp_getpdb(ispsoftc_t *, int, isp_pdb_t *); +static uint64_t isp_get_portname(ispsoftc_t *, int, int); +static int isp_fclink_test(ispsoftc_t *, int); static char *isp2100_fw_statename(int); -static int isp_pdb_sync(struct ispsoftc *); -static int isp_scan_loop(struct ispsoftc *); -static int isp_fabric_mbox_cmd(struct ispsoftc *, mbreg_t *); -static int isp_scan_fabric(struct ispsoftc *, int); -static void isp_register_fc4_type(struct ispsoftc *); -static void isp_fw_state(struct ispsoftc *); -static void isp_mboxcmd_qnw(struct ispsoftc *, mbreg_t *, int); -static void isp_mboxcmd(struct ispsoftc *, mbreg_t *, int); +static int isp_pdb_sync(ispsoftc_t *); +static int isp_scan_loop(ispsoftc_t *); +static int isp_fabric_mbox_cmd(ispsoftc_t *, mbreg_t *); +static int isp_scan_fabric(ispsoftc_t *, int); +static void isp_register_fc4_type(ispsoftc_t *); +static void isp_fw_state(ispsoftc_t *); +static void isp_mboxcmd_qnw(ispsoftc_t *, mbreg_t *, int); +static void isp_mboxcmd(ispsoftc_t *, mbreg_t *, int); -static void isp_update(struct ispsoftc *); -static void isp_update_bus(struct ispsoftc *, int); -static void isp_setdfltparm(struct ispsoftc *, int); -static int isp_read_nvram(struct ispsoftc *); -static void isp_rdnvram_word(struct ispsoftc *, int, uint16_t *); -static void isp_parse_nvram_1020(struct ispsoftc *, uint8_t *); -static void isp_parse_nvram_1080(struct ispsoftc *, int, uint8_t *); -static void isp_parse_nvram_12160(struct ispsoftc *, int, uint8_t *); -static void isp_parse_nvram_2100(struct ispsoftc *, uint8_t *); +static void isp_update(ispsoftc_t *); +static void isp_update_bus(ispsoftc_t *, int); +static void isp_setdfltparm(ispsoftc_t *, int); +static int isp_read_nvram(ispsoftc_t *); +static void isp_rdnvram_word(ispsoftc_t *, int, uint16_t *); +static void isp_parse_nvram_1020(ispsoftc_t *, uint8_t *); +static void isp_parse_nvram_1080(ispsoftc_t *, int, uint8_t *); +static void isp_parse_nvram_12160(ispsoftc_t *, int, uint8_t *); +static void isp_parse_nvram_2100(ispsoftc_t *, uint8_t *); /* * Reset Hardware. @@ -158,7 +158,7 @@ static void isp_parse_nvram_2100(struct ispsoftc *, uint8_t *); */ void -isp_reset(struct ispsoftc *isp) +isp_reset(ispsoftc_t *isp) { mbreg_t mbs; uint16_t code_org; @@ -837,7 +837,7 @@ again: */ void -isp_init(struct ispsoftc *isp) +isp_init(ispsoftc_t *isp) { /* * Must do this first to get defaults established. @@ -854,7 +854,7 @@ isp_init(struct ispsoftc *isp) } static void -isp_scsi_init(struct ispsoftc *isp) +isp_scsi_init(ispsoftc_t *isp) { sdparam *sdp_chan0, *sdp_chan1; mbreg_t mbs; @@ -1053,7 +1053,7 @@ isp_scsi_init(struct ispsoftc *isp) } static void -isp_scsi_channel_init(struct ispsoftc *isp, int channel) +isp_scsi_channel_init(ispsoftc_t *isp, int channel) { sdparam *sdp; mbreg_t mbs; @@ -1174,7 +1174,7 @@ isp_scsi_channel_init(struct ispsoftc *isp, int channel) * Locks are held before coming here. */ static void -isp_fibre_init(struct ispsoftc *isp) +isp_fibre_init(ispsoftc_t *isp) { fcparam *fcp; isp_icb_t local, *icbp = &local; @@ -1277,7 +1277,7 @@ isp_fibre_init(struct ispsoftc *isp) /* * We end up with these Loop IDs for F-Port topologies */ - if (icbp->icb_hardaddr != 0xff || icbp->icb_hardaddr != 0x800) { + if (icbp->icb_hardaddr != 0xff && icbp->icb_hardaddr != 0x800) { isp_prt(isp, ISP_LOGERR, "bad hard address %u- resetting to zero", icbp->icb_hardaddr); @@ -1390,7 +1390,8 @@ isp_fibre_init(struct ispsoftc *isp) mbs.param[3] = 0; isp_mboxcmd(isp, &mbs, MBLOGALL); } - icbp->icb_logintime = 30; /* 30 second login timeout */ + icbp->icb_logintime = ICB_LOGIN_TOV; + icbp->icb_lunetimeout = ICB_LUN_ENABLE_TOV; if (IS_23XX(isp)) { ISP_WRITE(isp, isp->isp_rqstinrp, 0); @@ -1472,7 +1473,7 @@ isp_fibre_init(struct ispsoftc *isp) */ static int -isp_getmap(struct ispsoftc *isp, fcpos_map_t *map) +isp_getmap(ispsoftc_t *isp, fcpos_map_t *map) { fcparam *fcp = (fcparam *) isp->isp_param; mbreg_t mbs; @@ -1504,7 +1505,7 @@ isp_getmap(struct ispsoftc *isp, fcpos_map_t *map) } static void -isp_mark_getpdb_all(struct ispsoftc *isp) +isp_mark_getpdb_all(ispsoftc_t *isp) { fcparam *fcp = (fcparam *) isp->isp_param; int i; @@ -1514,7 +1515,7 @@ isp_mark_getpdb_all(struct ispsoftc *isp) } static int -isp_getpdb(struct ispsoftc *isp, int id, isp_pdb_t *pdbp) +isp_getpdb(ispsoftc_t *isp, int id, isp_pdb_t *pdbp) { fcparam *fcp = (fcparam *) isp->isp_param; mbreg_t mbs; @@ -1550,7 +1551,7 @@ isp_getpdb(struct ispsoftc *isp, int id, isp_pdb_t *pdbp) } static uint64_t -isp_get_portname(struct ispsoftc *isp, int loopid, int nodename) +isp_get_portname(ispsoftc_t *isp, int loopid, int nodename) { uint64_t wwn = 0; mbreg_t mbs; @@ -1587,7 +1588,7 @@ isp_get_portname(struct ispsoftc *isp, int loopid, int nodename) */ static int -isp_fclink_test(struct ispsoftc *isp, int usdelay) +isp_fclink_test(ispsoftc_t *isp, int usdelay) { static char *toponames[] = { "Private Loop", @@ -1864,7 +1865,7 @@ isp2100_fw_statename(int state) */ static int -isp_pdb_sync(struct ispsoftc *isp) +isp_pdb_sync(ispsoftc_t *isp) { struct lportdb *lp; fcparam *fcp = isp->isp_param; @@ -2190,7 +2191,7 @@ dump_em: } static int -isp_scan_loop(struct ispsoftc *isp) +isp_scan_loop(ispsoftc_t *isp) { struct lportdb *lp; fcparam *fcp = isp->isp_param; @@ -2462,7 +2463,7 @@ isp_scan_loop(struct ispsoftc *isp) static int -isp_fabric_mbox_cmd(struct ispsoftc *isp, mbreg_t *mbp) +isp_fabric_mbox_cmd(ispsoftc_t *isp, mbreg_t *mbp) { isp_mboxcmd(isp, mbp, MBLOGNONE); if (mbp->param[0] != MBOX_COMMAND_COMPLETE) { @@ -2511,7 +2512,7 @@ isp_fabric_mbox_cmd(struct ispsoftc *isp, mbreg_t *mbp) #ifdef ISP_USE_GA_NXT static int -isp_scan_fabric(struct ispsoftc *isp, int ftype) +isp_scan_fabric(ispsoftc_t *isp, int ftype) { fcparam *fcp = isp->isp_param; uint32_t portid, first_portid, last_portid; @@ -2675,7 +2676,7 @@ isp_scan_fabric(struct ispsoftc *isp, int ftype) #define GXOFF (256) static int -isp_scan_fabric(struct ispsoftc *isp, int ftype) +isp_scan_fabric(ispsoftc_t *isp, int ftype) { fcparam *fcp = FCPARAM(isp); mbreg_t mbs; @@ -2981,7 +2982,7 @@ isp_scan_fabric(struct ispsoftc *isp, int ftype) #endif static void -isp_register_fc4_type(struct ispsoftc *isp) +isp_register_fc4_type(ispsoftc_t *isp) { fcparam *fcp = isp->isp_param; uint8_t local[SNS_RFT_ID_REQ_SIZE]; @@ -3028,7 +3029,7 @@ isp_register_fc4_type(struct ispsoftc *isp) int isp_start(XS_T *xs) { - struct ispsoftc *isp; + ispsoftc_t *isp; uint16_t nxti, optr, handle; uint8_t local[QENTRY_LEN]; ispreq_t *reqp, *qep; @@ -3401,7 +3402,7 @@ isp_start(XS_T *xs) */ int -isp_control(struct ispsoftc *isp, ispctl_t ctl, void *arg) +isp_control(ispsoftc_t *isp, ispctl_t ctl, void *arg) { XS_T *xs; mbreg_t mbs; @@ -3614,7 +3615,7 @@ isp_control(struct ispsoftc *isp, ispctl_t ctl, void *arg) #endif void -isp_intr(struct ispsoftc *isp, uint16_t isr, uint16_t sema, uint16_t mbox) +isp_intr(ispsoftc_t *isp, uint16_t isr, uint16_t sema, uint16_t mbox) { XS_T *complist[MAX_REQUESTQ_COMPLETIONS], *xs; uint16_t iptr, optr, junk; @@ -4059,7 +4060,7 @@ again: */ static int -isp_parse_async(struct ispsoftc *isp, uint16_t mbox) +isp_parse_async(ispsoftc_t *isp, uint16_t mbox) { int rval = 0; int bus; @@ -4414,7 +4415,7 @@ isp_parse_async(struct ispsoftc *isp, uint16_t mbox) */ static int -isp_handle_other_response(struct ispsoftc *isp, int type, +isp_handle_other_response(ispsoftc_t *isp, int type, isphdr_t *hp, uint16_t *optrp) { switch (type) { @@ -4464,7 +4465,7 @@ isp_handle_other_response(struct ispsoftc *isp, int type, } static void -isp_parse_status(struct ispsoftc *isp, ispstatusreq_t *sp, XS_T *xs) +isp_parse_status(ispsoftc_t *isp, ispstatusreq_t *sp, XS_T *xs) { switch (sp->req_completion_status & 0xff) { case RQCS_COMPLETE: @@ -4848,7 +4849,7 @@ isp_parse_status(struct ispsoftc *isp, ispstatusreq_t *sp, XS_T *xs) } static void -isp_fastpost_complete(struct ispsoftc *isp, uint16_t fph) +isp_fastpost_complete(ispsoftc_t *isp, uint16_t fph) { XS_T *xs; @@ -4881,7 +4882,7 @@ isp_fastpost_complete(struct ispsoftc *isp, uint16_t fph) } static int -isp_mbox_continue(struct ispsoftc *isp) +isp_mbox_continue(ispsoftc_t *isp) { mbreg_t mbs; uint16_t *ptr; @@ -5398,7 +5399,7 @@ static char *fc_mbcmd_names[] = { #endif static void -isp_mboxcmd_qnw(struct ispsoftc *isp, mbreg_t *mbp, int nodelay) +isp_mboxcmd_qnw(ispsoftc_t *isp, mbreg_t *mbp, int nodelay) { unsigned int ibits, obits, box, opcode; const uint32_t *mcp; @@ -5438,7 +5439,7 @@ isp_mboxcmd_qnw(struct ispsoftc *isp, mbreg_t *mbp, int nodelay) } static void -isp_mboxcmd(struct ispsoftc *isp, mbreg_t *mbp, int logmask) +isp_mboxcmd(ispsoftc_t *isp, mbreg_t *mbp, int logmask) { char *cname, *xname, tname[16], mname[16]; unsigned int lim, ibits, obits, box, opcode; @@ -5586,7 +5587,7 @@ isp_mboxcmd(struct ispsoftc *isp, mbreg_t *mbp, int logmask) } static void -isp_fw_state(struct ispsoftc *isp) +isp_fw_state(ispsoftc_t *isp) { if (IS_FC(isp)) { mbreg_t mbs; @@ -5602,7 +5603,7 @@ isp_fw_state(struct ispsoftc *isp) } static void -isp_update(struct ispsoftc *isp) +isp_update(ispsoftc_t *isp) { int bus, upmask; @@ -5615,7 +5616,7 @@ isp_update(struct ispsoftc *isp) } static void -isp_update_bus(struct ispsoftc *isp, int bus) +isp_update_bus(ispsoftc_t *isp, int bus) { int tgt; mbreg_t mbs; @@ -5740,7 +5741,7 @@ isp_update_bus(struct ispsoftc *isp, int bus) #endif static void -isp_setdfltparm(struct ispsoftc *isp, int channel) +isp_setdfltparm(ispsoftc_t *isp, int channel) { int tgt; mbreg_t mbs; @@ -5967,7 +5968,7 @@ isp_setdfltparm(struct ispsoftc *isp, int channel) */ void -isp_reinit(struct ispsoftc *isp) +isp_reinit(ispsoftc_t *isp) { XS_T *xs; int i; @@ -6013,7 +6014,7 @@ isp_reinit(struct ispsoftc *isp) * NVRAM Routines */ static int -isp_read_nvram(struct ispsoftc *isp) +isp_read_nvram(ispsoftc_t *isp) { int i, amt; uint8_t csum, minversion; @@ -6087,7 +6088,7 @@ isp_read_nvram(struct ispsoftc *isp) } static void -isp_rdnvram_word(struct ispsoftc *isp, int wo, uint16_t *rp) +isp_rdnvram_word(ispsoftc_t *isp, int wo, uint16_t *rp) { int i, cbits; uint16_t bit, rqst; @@ -6153,7 +6154,7 @@ isp_rdnvram_word(struct ispsoftc *isp, int wo, uint16_t *rp) } static void -isp_parse_nvram_1020(struct ispsoftc *isp, uint8_t *nvram_data) +isp_parse_nvram_1020(ispsoftc_t *isp, uint8_t *nvram_data) { sdparam *sdp = (sdparam *) isp->isp_param; int tgt; @@ -6279,7 +6280,7 @@ isp_parse_nvram_1020(struct ispsoftc *isp, uint8_t *nvram_data) } static void -isp_parse_nvram_1080(struct ispsoftc *isp, int bus, uint8_t *nvram_data) +isp_parse_nvram_1080(ispsoftc_t *isp, int bus, uint8_t *nvram_data) { sdparam *sdp = (sdparam *) isp->isp_param; int tgt; @@ -6371,7 +6372,7 @@ isp_parse_nvram_1080(struct ispsoftc *isp, int bus, uint8_t *nvram_data) } static void -isp_parse_nvram_12160(struct ispsoftc *isp, int bus, uint8_t *nvram_data) +isp_parse_nvram_12160(ispsoftc_t *isp, int bus, uint8_t *nvram_data) { sdparam *sdp = (sdparam *) isp->isp_param; int tgt; @@ -6462,7 +6463,7 @@ isp_parse_nvram_12160(struct ispsoftc *isp, int bus, uint8_t *nvram_data) } static void -isp_parse_nvram_2100(struct ispsoftc *isp, uint8_t *nvram_data) +isp_parse_nvram_2100(ispsoftc_t *isp, uint8_t *nvram_data) { fcparam *fcp = (fcparam *) isp->isp_param; uint64_t wwn; @@ -6554,11 +6555,11 @@ isp_parse_nvram_2100(struct ispsoftc *isp, uint8_t *nvram_data) } #ifdef ISP_FW_CRASH_DUMP -static void isp2200_fw_dump(struct ispsoftc *); -static void isp2300_fw_dump(struct ispsoftc *); +static void isp2200_fw_dump(ispsoftc_t *); +static void isp2300_fw_dump(ispsoftc_t *); static void -isp2200_fw_dump(struct ispsoftc *isp) +isp2200_fw_dump(ispsoftc_t *isp) { int i, j; mbreg_t mbs; @@ -6703,7 +6704,7 @@ isp2200_fw_dump(struct ispsoftc *isp) } static void -isp2300_fw_dump(struct ispsoftc *isp) +isp2300_fw_dump(ispsoftc_t *isp) { int i, j; mbreg_t mbs; @@ -6867,7 +6868,7 @@ isp2300_fw_dump(struct ispsoftc *isp) } void -isp_fw_dump(struct ispsoftc *isp) +isp_fw_dump(ispsoftc_t *isp) { if (IS_2200(isp)) isp2200_fw_dump(isp); diff --git a/sys/dev/isp/isp_freebsd.c b/sys/dev/isp/isp_freebsd.c index 07af6502ba151..f95b77df2e860 100644 --- a/sys/dev/isp/isp_freebsd.c +++ b/sys/dev/isp/isp_freebsd.c @@ -53,17 +53,36 @@ static void isp_kthread(void *); static void isp_action(struct cam_sim *, union ccb *); +#if __FreeBSD_version < 500000 +#define ISP_CDEV_MAJOR 248 +static struct cdevsw isp_cdevsw = { + /* open */ nullopen, + /* close */ nullclose, + /* read */ noread, + /* write */ nowrite, + /* ioctl */ ispioctl, + /* poll */ nopoll, + /* mmap */ nommap, + /* strategy */ nostrategy, + /* name */ "isp", + /* maj */ ISP_CDEV_MAJOR, + /* dump */ nodump, + /* psize */ nopsize, + /* flags */ D_TAPE, +}; +#else static struct cdevsw isp_cdevsw = { .d_version = D_VERSION, .d_flags = D_NEEDGIANT, .d_ioctl = ispioctl, .d_name = "isp", }; +#endif -static struct ispsoftc *isplist = NULL; +static ispsoftc_t *isplist = NULL; void -isp_attach(struct ispsoftc *isp) +isp_attach(ispsoftc_t *isp) { int primary, secondary; struct ccb_setasync csa; @@ -140,11 +159,17 @@ isp_attach(struct ispsoftc *isp) */ if (IS_FC(isp)) { ISPLOCK_2_CAMLOCK(isp); +#if __FreeBSD_version >= 500000 /* XXX: LOCK VIOLATION */ cv_init(&isp->isp_osinfo.kthread_cv, "isp_kthread_cv"); if (kthread_create(isp_kthread, isp, &isp->isp_osinfo.kproc, RFHIGHPID, 0, "%s: fc_thrd", - device_get_nameunit(isp->isp_dev))) { + device_get_nameunit(isp->isp_dev))) +#else + if (kthread_create(isp_kthread, isp, &isp->isp_osinfo.kproc, + "%s: fc_thrd", device_get_nameunit(isp->isp_dev))) +#endif + { xpt_bus_deregister(cam_sim_path(sim)); cam_sim_free(sim, TRUE); config_intrhook_disestablish(&isp->isp_osinfo.ehook); @@ -214,7 +239,7 @@ isp_attach(struct ispsoftc *isp) if (isplist == NULL) { isplist = isp; } else { - struct ispsoftc *tmp = isplist; + ispsoftc_t *tmp = isplist; while (tmp->isp_osinfo.next) { tmp = tmp->isp_osinfo.next; } @@ -224,7 +249,7 @@ isp_attach(struct ispsoftc *isp) } static __inline void -isp_freeze_loopdown(struct ispsoftc *isp, char *msg) +isp_freeze_loopdown(ispsoftc_t *isp, char *msg) { if (isp->isp_osinfo.simqfrozen == 0) { isp_prt(isp, ISP_LOGDEBUG0, "%s: freeze simq (loopdown)", msg); @@ -238,10 +263,19 @@ isp_freeze_loopdown(struct ispsoftc *isp, char *msg) } } + +#if __FreeBSD_version < 500000 +#define _DEV dev_t +#define _IOP struct proc +#else +#define _IOP struct thread +#define _DEV struct cdev * +#endif + static int -ispioctl(struct cdev *dev, u_long c, caddr_t addr, int flags, struct thread *td) +ispioctl(_DEV dev, u_long c, caddr_t addr, int flags, _IOP *td) { - struct ispsoftc *isp; + ispsoftc_t *isp; int nr, retval = ENOTTY; isp = isplist; @@ -577,7 +611,7 @@ ispioctl(struct cdev *dev, u_long c, caddr_t addr, int flags, struct thread *td) static void isp_intr_enable(void *arg) { - struct ispsoftc *isp = arg; + ispsoftc_t *isp = arg; if (isp->isp_role != ISP_ROLE_NONE) { ENABLE_INTS(isp); #if 0 @@ -594,29 +628,29 @@ isp_intr_enable(void *arg) #ifdef ISP_TARGET_MODE -static __inline int is_lun_enabled(struct ispsoftc *, int, lun_id_t); -static __inline int are_any_luns_enabled(struct ispsoftc *, int); -static __inline tstate_t *get_lun_statep(struct ispsoftc *, int, lun_id_t); -static __inline void rls_lun_statep(struct ispsoftc *, tstate_t *); -static __inline atio_private_data_t *isp_get_atpd(struct ispsoftc *, int); +static __inline int is_lun_enabled(ispsoftc_t *, int, lun_id_t); +static __inline int are_any_luns_enabled(ispsoftc_t *, int); +static __inline tstate_t *get_lun_statep(ispsoftc_t *, int, lun_id_t); +static __inline void rls_lun_statep(ispsoftc_t *, tstate_t *); +static __inline atio_private_data_t *isp_get_atpd(ispsoftc_t *, int); static cam_status -create_lun_state(struct ispsoftc *, int, struct cam_path *, tstate_t **); -static void destroy_lun_state(struct ispsoftc *, tstate_t *); -static int isp_en_lun(struct ispsoftc *, union ccb *); -static void isp_ledone(struct ispsoftc *, lun_entry_t *); -static cam_status isp_abort_tgt_ccb(struct ispsoftc *, union ccb *); +create_lun_state(ispsoftc_t *, int, struct cam_path *, tstate_t **); +static void destroy_lun_state(ispsoftc_t *, tstate_t *); +static int isp_en_lun(ispsoftc_t *, union ccb *); +static void isp_ledone(ispsoftc_t *, lun_entry_t *); +static cam_status isp_abort_tgt_ccb(ispsoftc_t *, union ccb *); static timeout_t isp_refire_putback_atio; static void isp_complete_ctio(union ccb *); static void isp_target_putback_atio(union ccb *); -static cam_status isp_target_start_ctio(struct ispsoftc *, union ccb *); -static int isp_handle_platform_atio(struct ispsoftc *, at_entry_t *); -static int isp_handle_platform_atio2(struct ispsoftc *, at2_entry_t *); -static int isp_handle_platform_ctio(struct ispsoftc *, void *); -static int isp_handle_platform_notify_scsi(struct ispsoftc *, in_entry_t *); -static int isp_handle_platform_notify_fc(struct ispsoftc *, in_fcentry_t *); +static void isp_target_start_ctio(ispsoftc_t *, union ccb *); +static int isp_handle_platform_atio(ispsoftc_t *, at_entry_t *); +static int isp_handle_platform_atio2(ispsoftc_t *, at2_entry_t *); +static int isp_handle_platform_ctio(ispsoftc_t *, void *); +static int isp_handle_platform_notify_scsi(ispsoftc_t *, in_entry_t *); +static int isp_handle_platform_notify_fc(ispsoftc_t *, in_fcentry_t *); static __inline int -is_lun_enabled(struct ispsoftc *isp, int bus, lun_id_t lun) +is_lun_enabled(ispsoftc_t *isp, int bus, lun_id_t lun) { tstate_t *tptr; tptr = isp->isp_osinfo.lun_hash[LUN_HASH_FUNC(isp, bus, lun)]; @@ -632,7 +666,7 @@ is_lun_enabled(struct ispsoftc *isp, int bus, lun_id_t lun) } static __inline int -are_any_luns_enabled(struct ispsoftc *isp, int port) +are_any_luns_enabled(ispsoftc_t *isp, int port) { int lo, hi; if (IS_DUALBUS(isp)) { @@ -651,7 +685,7 @@ are_any_luns_enabled(struct ispsoftc *isp, int port) } static __inline tstate_t * -get_lun_statep(struct ispsoftc *isp, int bus, lun_id_t lun) +get_lun_statep(ispsoftc_t *isp, int bus, lun_id_t lun) { tstate_t *tptr = NULL; @@ -679,14 +713,14 @@ get_lun_statep(struct ispsoftc *isp, int bus, lun_id_t lun) } static __inline void -rls_lun_statep(struct ispsoftc *isp, tstate_t *tptr) +rls_lun_statep(ispsoftc_t *isp, tstate_t *tptr) { if (tptr->hold) tptr->hold--; } static __inline atio_private_data_t * -isp_get_atpd(struct ispsoftc *isp, int tag) +isp_get_atpd(ispsoftc_t *isp, int tag) { atio_private_data_t *atp; for (atp = isp->isp_osinfo.atpdp; @@ -698,7 +732,7 @@ isp_get_atpd(struct ispsoftc *isp, int tag) } static cam_status -create_lun_state(struct ispsoftc *isp, int bus, +create_lun_state(ispsoftc_t *isp, int bus, struct cam_path *path, tstate_t **rslt) { cam_status status; @@ -744,7 +778,7 @@ create_lun_state(struct ispsoftc *isp, int bus, } static __inline void -destroy_lun_state(struct ispsoftc *isp, tstate_t *tptr) +destroy_lun_state(ispsoftc_t *isp, tstate_t *tptr) { int hfx; tstate_t *lw, *pw; @@ -780,7 +814,7 @@ destroy_lun_state(struct ispsoftc *isp, tstate_t *tptr) * Enable luns. */ static int -isp_en_lun(struct ispsoftc *isp, union ccb *ccb) +isp_en_lun(ispsoftc_t *isp, union ccb *ccb) { struct ccb_en_lun *cel = &ccb->cel; tstate_t *tptr; @@ -1023,7 +1057,7 @@ isp_en_lun(struct ispsoftc *isp, union ccb *ccb) } static void -isp_ledone(struct ispsoftc *isp, lun_entry_t *lep) +isp_ledone(ispsoftc_t *isp, lun_entry_t *lep) { const char lfmt[] = "lun %d now %sabled for target mode on channel %d"; union ccb *ccb; @@ -1073,7 +1107,7 @@ err: if (cel->enable) { ccb->ccb_h.status = CAM_REQ_CMP; - isp_prt(isp, /* ISP_LOGINFO */ ISP_LOGALL, lfmt, + isp_prt(isp, ISP_LOGINFO, lfmt, XS_LUN(ccb), "en", XS_CHANNEL(ccb)); rls_lun_statep(isp, tptr); isp->isp_osinfo.leact[seq] = 0; @@ -1119,7 +1153,7 @@ err: static cam_status -isp_abort_tgt_ccb(struct ispsoftc *isp, union ccb *ccb) +isp_abort_tgt_ccb(ispsoftc_t *isp, union ccb *ccb) { tstate_t *tptr; struct ccb_hdr_slist *lp; @@ -1197,8 +1231,8 @@ isp_abort_tgt_ccb(struct ispsoftc *isp, union ccb *ccb) return (CAM_PATH_INVALID); } -static cam_status -isp_target_start_ctio(struct ispsoftc *isp, union ccb *ccb) +static void +isp_target_start_ctio(ispsoftc_t *isp, union ccb *ccb) { void *qe; struct ccb_scsiio *cso = &ccb->csio; @@ -1210,7 +1244,8 @@ isp_target_start_ctio(struct ispsoftc *isp, union ccb *ccb) if (isp_getrqentry(isp, &nxti, &optr, &qe)) { xpt_print_path(ccb->ccb_h.path); printf("Request Queue Overflow in isp_target_start_ctio\n"); - return (CAM_RESRC_UNAVAIL); + XS_SETERR(ccb, CAM_REQUEUE_REQ); + goto out; } bzero(local, QENTRY_LEN); @@ -1234,7 +1269,8 @@ isp_target_start_ctio(struct ispsoftc *isp, union ccb *ccb) isp_prt(isp, ISP_LOGERR, "cannot find private data adjunct for tag %x", cso->tag_id); - return (-1); + XS_SETERR(ccb, CAM_REQ_CMP_ERR); + goto out; } cto->ct_rxid = cso->tag_id; @@ -1297,8 +1333,9 @@ isp_target_start_ctio(struct ispsoftc *isp, union ccb *ccb) cso->dxfer_len, cto->ct_resid); cto->ct_flags |= CT2_CCINCR; atp->state = ATPD_STATE_LAST_CTIO; - } else + } else { atp->state = ATPD_STATE_CTIO; + } cto->ct_timeout = 10; hp = &cto->ct_syshandle; } else { @@ -1342,7 +1379,8 @@ isp_target_start_ctio(struct ispsoftc *isp, union ccb *ccb) if (isp_save_xs_tgt(isp, ccb, hp)) { xpt_print_path(ccb->ccb_h.path); printf("No XFLIST pointers for isp_target_start_ctio\n"); - return (CAM_RESRC_UNAVAIL); + XS_SETERR(ccb, CAM_REQUEUE_REQ); + goto out; } @@ -1360,17 +1398,22 @@ isp_target_start_ctio(struct ispsoftc *isp, union ccb *ccb) switch (ISP_DMASETUP(isp, cso, (ispreq_t *) local, &nxti, optr)) { case CMD_QUEUED: ISP_ADD_REQUEST(isp, nxti); - return (CAM_REQ_INPROG); + ccb->ccb_h.status |= CAM_SIM_QUEUED; + return; case CMD_EAGAIN: - ccb->ccb_h.status = CAM_RESRC_UNAVAIL; - isp_destroy_tgt_handle(isp, save_handle); - return (CAM_RESRC_UNAVAIL); + XS_SETERR(ccb, CAM_REQUEUE_REQ); + break; default: - isp_destroy_tgt_handle(isp, save_handle); - return (XS_ERR(ccb)); + break; } + isp_destroy_tgt_handle(isp, save_handle); + +out: + ISPLOCK_2_CAMLOCK(isp); + xpt_done(ccb); + CAMLOCK_2_ISPLOCK(isp); } static void @@ -1384,7 +1427,7 @@ isp_refire_putback_atio(void *arg) static void isp_target_putback_atio(union ccb *ccb) { - struct ispsoftc *isp; + ispsoftc_t *isp; struct ccb_scsiio *cso; uint16_t nxti, optr; void *qe; @@ -1435,11 +1478,13 @@ isp_target_putback_atio(union ccb *ccb) static void isp_complete_ctio(union ccb *ccb) { + ISPLOCK_2_CAMLOCK(isp); if ((ccb->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_INPROG) { ccb->ccb_h.status |= CAM_REQ_CMP; } ccb->ccb_h.status &= ~CAM_SIM_QUEUED; xpt_done(ccb); + CAMLOCK_2_ISPLOCK(isp); } /* @@ -1448,7 +1493,7 @@ isp_complete_ctio(union ccb *ccb) */ static int -isp_handle_platform_atio(struct ispsoftc *isp, at_entry_t *aep) +isp_handle_platform_atio(ispsoftc_t *isp, at_entry_t *aep) { tstate_t *tptr; int status, bus, iswildcard; @@ -1578,7 +1623,7 @@ isp_handle_platform_atio(struct ispsoftc *isp, at_entry_t *aep) } static int -isp_handle_platform_atio2(struct ispsoftc *isp, at2_entry_t *aep) +isp_handle_platform_atio2(ispsoftc_t *isp, at2_entry_t *aep) { lun_id_t lun; tstate_t *tptr; @@ -1694,7 +1739,7 @@ isp_handle_platform_atio2(struct ispsoftc *isp, at2_entry_t *aep) } static int -isp_handle_platform_ctio(struct ispsoftc *isp, void *arg) +isp_handle_platform_ctio(ispsoftc_t *isp, void *arg) { union ccb *ccb; int sentstatus, ok, notify_cam, resid = 0; @@ -1802,13 +1847,13 @@ isp_handle_platform_ctio(struct ispsoftc *isp, void *arg) } static int -isp_handle_platform_notify_scsi(struct ispsoftc *isp, in_entry_t *inp) +isp_handle_platform_notify_scsi(ispsoftc_t *isp, in_entry_t *inp) { return (0); /* XXXX */ } static int -isp_handle_platform_notify_fc(struct ispsoftc *isp, in_fcentry_t *inp) +isp_handle_platform_notify_fc(ispsoftc_t *isp, in_fcentry_t *inp) { switch (inp->in_status) { @@ -1872,10 +1917,10 @@ static void isp_cam_async(void *cbarg, uint32_t code, struct cam_path *path, void *arg) { struct cam_sim *sim; - struct ispsoftc *isp; + ispsoftc_t *isp; sim = (struct cam_sim *)cbarg; - isp = (struct ispsoftc *) cam_sim_softc(sim); + isp = (ispsoftc_t *) cam_sim_softc(sim); switch (code) { case AC_LOST_DEVICE: if (IS_SCSI(isp)) { @@ -1916,7 +1961,7 @@ isp_cam_async(void *cbarg, uint32_t code, struct cam_path *path, void *arg) static void isp_poll(struct cam_sim *sim) { - struct ispsoftc *isp = cam_sim_softc(sim); + ispsoftc_t *isp = cam_sim_softc(sim); uint16_t isr, sema, mbox; ISP_LOCK(isp); @@ -1931,7 +1976,7 @@ static void isp_watchdog(void *arg) { XS_T *xs = arg; - struct ispsoftc *isp = XS_ISP(xs); + ispsoftc_t *isp = XS_ISP(xs); uint32_t handle; int iok; @@ -2018,13 +2063,21 @@ isp_watchdog(void *arg) static void isp_kthread(void *arg) { - struct ispsoftc *isp = arg; + ispsoftc_t *isp = arg; + + +#if __FreeBSD_version < 500000 + int s; + s = splcam(); + isp->isp_osinfo.intsok = 1; +#else #ifdef ISP_SMPLOCK mtx_lock(&isp->isp_lock); #else mtx_lock(&Giant); #endif +#endif /* * The first loop is for our usage where we have yet to have * gotten good fibre channel state. @@ -2065,11 +2118,15 @@ isp_kthread(void *arg) CAMLOCK_2_ISPLOCK(isp); } isp_prt(isp, ISP_LOGDEBUG0, "kthread: waiting until called"); +#if __FreeBSD_version < 500000 + tsleep(&isp->isp_osinfo.kproc, PRIBIO, "isp_fc_worker", 0); +#else #ifdef ISP_SMPLOCK cv_wait(&isp->isp_osinfo.kthread_cv, &isp->isp_lock); #else (void) tsleep(&isp->isp_osinfo.kthread_cv, PRIBIO, "fc_cv", 0); #endif +#endif } } @@ -2077,12 +2134,12 @@ static void isp_action(struct cam_sim *sim, union ccb *ccb) { int bus, tgt, error; - struct ispsoftc *isp; + ispsoftc_t *isp; struct ccb_trans_settings *cts; CAM_DEBUG(ccb->ccb_h.path, CAM_DEBUG_TRACE, ("isp_action\n")); - isp = (struct ispsoftc *)cam_sim_softc(sim); + isp = (ispsoftc_t *)cam_sim_softc(sim); ccb->ccb_h.sim_priv.entries[0].field = 0; ccb->ccb_h.sim_priv.entries[1].ptr = isp; if (isp->isp_state != ISP_RUNSTATE && @@ -2168,11 +2225,15 @@ isp_action(struct cam_sim *sim, union ccb *ccb) xpt_done(ccb); break; } +#if __FreeBSD_version < 500000 + wakeup(&isp->isp_osinfo.kproc); +#else #ifdef ISP_SMPLOCK cv_signal(&isp->isp_osinfo.kthread_cv); #else wakeup(&isp->isp_osinfo.kthread_cv); #endif +#endif isp_freeze_loopdown(isp, "isp_action(RQLATER)"); XS_SETERR(ccb, CAM_REQUEUE_REQ); ISPLOCK_2_CAMLOCK(isp); @@ -2267,18 +2328,8 @@ isp_action(struct cam_sim *sim, union ccb *ccb) case XPT_CONT_TARGET_IO: { CAMLOCK_2_ISPLOCK(isp); - ccb->ccb_h.status = isp_target_start_ctio(isp, ccb); - if (ccb->ccb_h.status != CAM_REQ_INPROG) { - isp_prt(isp, ISP_LOGWARN, - "XPT_CONT_TARGET_IO: status 0x%x", - ccb->ccb_h.status); - XS_SETERR(ccb, CAM_REQUEUE_REQ); - ISPLOCK_2_CAMLOCK(isp); - xpt_done(ccb); - } else { - ISPLOCK_2_CAMLOCK(isp); - ccb->ccb_h.status |= CAM_SIM_QUEUED; - } + isp_target_start_ctio(isp, ccb); + ISPLOCK_2_CAMLOCK(isp); break; } #endif @@ -2609,22 +2660,39 @@ isp_action(struct cam_sim *sim, union ccb *ccb) break; case XPT_CALC_GEOMETRY: +#if __FreeBSD_version < 500000 { struct ccb_calc_geometry *ccg; + u_int32_t secs_per_cylinder; + u_int32_t size_mb; ccg = &ccb->ccg; if (ccg->block_size == 0) { - isp_prt(isp, ISP_LOGERR, - "%d.%d XPT_CALC_GEOMETRY block size 0?", - ccg->ccb_h.target_id, ccg->ccb_h.target_lun); ccb->ccb_h.status = CAM_REQ_INVALID; xpt_done(ccb); break; } - cam_calc_geometry(ccg, /*extended*/1); + size_mb = ccg->volume_size /((1024L * 1024L) / ccg->block_size); + if (size_mb > 1024) { + ccg->heads = 255; + ccg->secs_per_track = 63; + } else { + ccg->heads = 64; + ccg->secs_per_track = 32; + } + secs_per_cylinder = ccg->heads * ccg->secs_per_track; + ccg->cylinders = ccg->volume_size / secs_per_cylinder; + ccb->ccb_h.status = CAM_REQ_CMP; + xpt_done(ccb); + break; + } +#else + { + cam_calc_geometry(&ccb->ccg, /*extended*/1); xpt_done(ccb); break; } +#endif case XPT_RESET_BUS: /* Reset the specified bus */ bus = cam_sim_bus(sim); CAMLOCK_2_ISPLOCK(isp); @@ -2719,7 +2787,7 @@ isp_action(struct cam_sim *sim, union ccb *ccb) void isp_done(struct ccb_scsiio *sccb) { - struct ispsoftc *isp = XS_ISP(sccb); + ispsoftc_t *isp = XS_ISP(sccb); if (XS_NOERR(sccb)) XS_SETERR(sccb, CAM_REQ_CMP); @@ -2769,7 +2837,7 @@ isp_done(struct ccb_scsiio *sccb) } int -isp_async(struct ispsoftc *isp, ispasync_t cmd, void *arg) +isp_async(ispsoftc_t *isp, ispasync_t cmd, void *arg) { int bus, rv = 0; switch (cmd) { @@ -2907,7 +2975,6 @@ isp_async(struct ispsoftc *isp, ispasync_t cmd, void *arg) break; case ISPASYNC_PROMENADE: { - struct cam_path *tmppath; const char *fmt = "Target %d (Loop 0x%x) Port ID 0x%x " "(role %s) %s\n Port WWN 0x%08x%08x\n Node WWN 0x%08x%08x"; static const char *roles[4] = { @@ -2915,7 +2982,10 @@ isp_async(struct ispsoftc *isp, ispasync_t cmd, void *arg) }; fcparam *fcp = isp->isp_param; int tgt = *((int *) arg); +#if __FreeBSD_version >= 500000 int is_tgt_mask = (SVC3_TGT_ROLE >> SVC3_ROLE_SHIFT); + struct cam_path *tmppath; +#endif struct lportdb *lp = &fcp->portdb[tgt]; isp_prt(isp, ISP_LOGINFO, fmt, tgt, lp->loopid, lp->portid, @@ -2927,6 +2997,7 @@ isp_async(struct ispsoftc *isp, ispasync_t cmd, void *arg) (uint32_t) (lp->node_wwn & 0xffffffffLL)); ISPLOCK_2_CAMLOCK(isp); +#if __FreeBSD_version >= 500000 if (xpt_create_path(&tmppath, NULL, cam_sim_path(isp->isp_sim), (target_id_t)tgt, CAM_LUN_WILDCARD) != CAM_REQ_CMP) { CAMLOCK_2_ISPLOCK(isp); @@ -2943,6 +3014,7 @@ isp_async(struct ispsoftc *isp, ispasync_t cmd, void *arg) } } xpt_free_path(tmppath); +#endif CAMLOCK_2_ISPLOCK(isp); break; } @@ -2954,11 +3026,15 @@ isp_async(struct ispsoftc *isp, ispasync_t cmd, void *arg) isp_prt(isp, ISP_LOGINFO, "Name Server Database Changed"); } +#if __FreeBSD_version < 500000 + wakeup(&isp->isp_osinfo.kproc); +#else #ifdef ISP_SMPLOCK cv_signal(&isp->isp_osinfo.kthread_cv); #else wakeup(&isp->isp_osinfo.kthread_cv); #endif +#endif break; case ISPASYNC_FABRIC_DEV: { @@ -3154,14 +3230,14 @@ isp_async(struct ispsoftc *isp, ispasync_t cmd, void *arg) * Locks are held before coming here. */ void -isp_uninit(struct ispsoftc *isp) +isp_uninit(ispsoftc_t *isp) { ISP_WRITE(isp, HCCR, HCCR_CMD_RESET); DISABLE_INTS(isp); } void -isp_prt(struct ispsoftc *isp, int level, const char *fmt, ...) +isp_prt(ispsoftc_t *isp, int level, const char *fmt, ...) { va_list ap; if (level != ISP_LOGALL && (level & isp->isp_dblev) == 0) { diff --git a/sys/dev/isp/isp_freebsd.h b/sys/dev/isp/isp_freebsd.h index 7e69e6196a2ef..3163b65abdf05 100644 --- a/sys/dev/isp/isp_freebsd.h +++ b/sys/dev/isp/isp_freebsd.h @@ -29,18 +29,30 @@ #ifndef _ISP_FREEBSD_H #define _ISP_FREEBSD_H +#if __FreeBSD_version < 500000 +#define ISP_PLATFORM_VERSION_MAJOR 4 +#define ISP_PLATFORM_VERSION_MINOR 17 +#else #define ISP_PLATFORM_VERSION_MAJOR 5 #define ISP_PLATFORM_VERSION_MINOR 9 +#endif #include <sys/param.h> #include <sys/systm.h> #include <sys/endian.h> +#if __FreeBSD_version < 500000 #include <sys/kernel.h> #include <sys/queue.h> +#include <sys/malloc.h> +#else #include <sys/lock.h> +#include <sys/kernel.h> +#include <sys/queue.h> #include <sys/malloc.h> #include <sys/mutex.h> #include <sys/condvar.h> +#endif + #include <sys/proc.h> #include <sys/bus.h> @@ -73,11 +85,15 @@ #define HANDLE_LOOPSTATE_IN_OUTER_LAYERS 1 /* #define ISP_SMPLOCK 1 */ +#if __FreeBSD_version < 500000 +#define ISP_IFLAGS INTR_TYPE_CAM +#else #ifdef ISP_SMPLOCK #define ISP_IFLAGS INTR_TYPE_CAM | INTR_ENTROPY | INTR_MPSAFE #else #define ISP_IFLAGS INTR_TYPE_CAM | INTR_ENTROPY #endif +#endif typedef void ispfwfunc(int, int, int, uint16_t **); @@ -129,14 +145,17 @@ struct isposinfo { struct cam_sim *sim2; struct cam_path *path2; struct intr_config_hook ehook; - uint8_t : 1, + uint8_t + disabled : 1, fcbsy : 1, ktmature : 1, mboxwaiting : 1, intsok : 1, simqfrozen : 3; +#if __FreeBSD_version >= 500000 struct mtx lock; struct cv kthread_cv; +#endif struct proc *kproc; bus_dma_tag_t cdmat; bus_dmamap_t cdmap; @@ -247,7 +266,7 @@ default: \ #define XS_T struct ccb_scsiio #define XS_DMA_ADDR_T bus_addr_t -#define XS_ISP(ccb) ((struct ispsoftc *) (ccb)->ccb_h.spriv_ptr1) +#define XS_ISP(ccb) ((ispsoftc_t *) (ccb)->ccb_h.spriv_ptr1) #define XS_CHANNEL(ccb) cam_sim_bus(xpt_path_sim((ccb)->ccb_h.path)) #define XS_TGT(ccb) (ccb)->ccb_h.target_id #define XS_LUN(ccb) (ccb)->ccb_h.target_lun @@ -359,7 +378,7 @@ default: \ #include <dev/isp/isp_tpublic.h> #endif -void isp_prt(struct ispsoftc *, int level, const char *, ...) +void isp_prt(ispsoftc_t *, int level, const char *, ...) __printflike(3, 4); /* * isp_osinfo definiitions && shorthand @@ -377,8 +396,8 @@ void isp_prt(struct ispsoftc *, int level, const char *, ...) /* * prototypes for isp_pci && isp_freebsd to share */ -extern void isp_attach(struct ispsoftc *); -extern void isp_uninit(struct ispsoftc *); +extern void isp_attach(ispsoftc_t *); +extern void isp_uninit(ispsoftc_t *); /* * driver global data @@ -411,9 +430,9 @@ extern int isp_announced; * Platform specific inline functions */ -static __inline void isp_mbox_wait_complete(struct ispsoftc *); +static __inline void isp_mbox_wait_complete(ispsoftc_t *); static __inline void -isp_mbox_wait_complete(struct ispsoftc *isp) +isp_mbox_wait_complete(ispsoftc_t *isp) { if (isp->isp_osinfo.intsok) { int lim = ((isp->isp_mbxwrk0)? 120 : 20) * hz; diff --git a/sys/dev/isp/isp_ioctl.h b/sys/dev/isp/isp_ioctl.h index 7b4890204bd19..d1f3f6754f0c7 100644 --- a/sys/dev/isp/isp_ioctl.h +++ b/sys/dev/isp/isp_ioctl.h @@ -46,7 +46,7 @@ #define ISP_RESETHBA _IO(ISP_IOC, 2) /* - * This ioctl performs a fibre chanel rescan. + * This ioctl performs a fibre channel rescan. */ #define ISP_RESCAN _IO(ISP_IOC, 3) diff --git a/sys/dev/isp/isp_pci.c b/sys/dev/isp/isp_pci.c index 0fe148cb05901..c261cca404244 100644 --- a/sys/dev/isp/isp_pci.c +++ b/sys/dev/isp/isp_pci.c @@ -36,11 +36,17 @@ __FBSDID("$FreeBSD$"); #include <sys/kernel.h> #include <sys/module.h> #include <sys/bus.h> +#if __FreeBSD_version < 500000 +#include <sys/bus.h> +#include <pci/pcireg.h> +#include <pci/pcivar.h> +#include <machine/bus_memio.h> +#include <machine/bus_pio.h> +#else #include <sys/stdint.h> - #include <dev/pci/pcireg.h> #include <dev/pci/pcivar.h> - +#endif #include <machine/bus.h> #include <machine/resource.h> #include <sys/rman.h> @@ -48,22 +54,26 @@ __FBSDID("$FreeBSD$"); #include <dev/isp/isp_freebsd.h> -static uint16_t isp_pci_rd_reg(struct ispsoftc *, int); -static void isp_pci_wr_reg(struct ispsoftc *, int, uint16_t); -static uint16_t isp_pci_rd_reg_1080(struct ispsoftc *, int); -static void isp_pci_wr_reg_1080(struct ispsoftc *, int, uint16_t); +#if __FreeBSD_version < 500000 +#define BUS_PROBE_DEFAULT 0 +#endif + +static uint16_t isp_pci_rd_reg(ispsoftc_t *, int); +static void isp_pci_wr_reg(ispsoftc_t *, int, uint16_t); +static uint16_t isp_pci_rd_reg_1080(ispsoftc_t *, int); +static void isp_pci_wr_reg_1080(ispsoftc_t *, int, uint16_t); static int -isp_pci_rd_isr(struct ispsoftc *, uint16_t *, uint16_t *, uint16_t *); +isp_pci_rd_isr(ispsoftc_t *, uint16_t *, uint16_t *, uint16_t *); static int -isp_pci_rd_isr_2300(struct ispsoftc *, uint16_t *, uint16_t *, uint16_t *); -static int isp_pci_mbxdma(struct ispsoftc *); +isp_pci_rd_isr_2300(ispsoftc_t *, uint16_t *, uint16_t *, uint16_t *); +static int isp_pci_mbxdma(ispsoftc_t *); static int -isp_pci_dmasetup(struct ispsoftc *, XS_T *, ispreq_t *, uint16_t *, uint16_t); +isp_pci_dmasetup(ispsoftc_t *, XS_T *, ispreq_t *, uint16_t *, uint16_t); static void -isp_pci_dmateardown(struct ispsoftc *, XS_T *, uint16_t); +isp_pci_dmateardown(ispsoftc_t *, XS_T *, uint16_t); -static void isp_pci_reset1(struct ispsoftc *); -static void isp_pci_dumpregs(struct ispsoftc *, const char *); +static void isp_pci_reset1(ispsoftc_t *); +static void isp_pci_dumpregs(ispsoftc_t *, const char *); static struct ispmdvec mdvec = { isp_pci_rd_isr, @@ -283,7 +293,7 @@ static int isp_pci_attach (device_t); struct isp_pcisoftc { - struct ispsoftc pci_isp; + ispsoftc_t pci_isp; device_t pci_dev; struct resource * pci_reg; bus_space_tag_t pci_st; @@ -372,70 +382,354 @@ isp_pci_probe(device_t dev) return (BUS_PROBE_DEFAULT); } -static int -isp_pci_attach(device_t dev) +#if __FreeBSD_version < 500000 +static void +isp_get_options(device_t dev, ispsoftc_t *isp) { - struct resource *regs, *irq; - int tval, rtp, rgd, iqd, m1, m2, isp_debug, role; - uint32_t data, cmd, linesz, psize, basetype; - struct isp_pcisoftc *pcs; - struct ispsoftc *isp = NULL; - struct ispmdvec *mdvp; - const char *sptr; - int locksetup = 0; + uint64_t wwn; + int bitmap, unit; + + unit = device_get_unit(dev); + if (getenv_int("isp_disable", &bitmap)) { + if (bitmap & (1 << unit)) { + isp->isp_osinfo.disabled = 1; + return; + } + } + + if (getenv_int("isp_no_fwload", &bitmap)) { + if (bitmap & (1 << unit)) + isp->isp_confopts |= ISP_CFG_NORELOAD; + } + if (getenv_int("isp_fwload", &bitmap)) { + if (bitmap & (1 << unit)) + isp->isp_confopts &= ~ISP_CFG_NORELOAD; + } + if (getenv_int("isp_no_nvram", &bitmap)) { + if (bitmap & (1 << unit)) + isp->isp_confopts |= ISP_CFG_NONVRAM; + } + if (getenv_int("isp_nvram", &bitmap)) { + if (bitmap & (1 << unit)) + isp->isp_confopts &= ~ISP_CFG_NONVRAM; + } + if (getenv_int("isp_fcduplex", &bitmap)) { + if (bitmap & (1 << unit)) + isp->isp_confopts |= ISP_CFG_FULL_DUPLEX; + } + if (getenv_int("isp_no_fcduplex", &bitmap)) { + if (bitmap & (1 << unit)) + isp->isp_confopts &= ~ISP_CFG_FULL_DUPLEX; + } + if (getenv_int("isp_nport", &bitmap)) { + if (bitmap & (1 << unit)) + isp->isp_confopts |= ISP_CFG_NPORT; + } /* + * Because the resource_*_value functions can neither return + * 64 bit integer values, nor can they be directly coerced + * to interpret the right hand side of the assignment as + * you want them to interpret it, we have to force WWN + * hint replacement to specify WWN strings with a leading + * 'w' (e..g w50000000aaaa0001). Sigh. + */ + if (getenv_quad("isp_portwwn", &wwn)) { + isp->isp_osinfo.default_port_wwn = wwn; + isp->isp_confopts |= ISP_CFG_OWNWWPN; + } + if (isp->isp_osinfo.default_port_wwn == 0) { + isp->isp_osinfo.default_port_wwn = 0x400000007F000009ull; + } + + if (getenv_quad("isp_nodewwn", &wwn)) { + isp->isp_osinfo.default_node_wwn = wwn; + isp->isp_confopts |= ISP_CFG_OWNWWNN; + } + if (isp->isp_osinfo.default_node_wwn == 0) { + isp->isp_osinfo.default_node_wwn = 0x400000007F000009ull; + } + + bitmap = 0; + (void) getenv_int("isp_debug", &bitmap); + if (bitmap) { + isp->isp_dblev = bitmap; + } else { + isp->isp_dblev = ISP_LOGWARN|ISP_LOGERR; + } + if (bootverbose) { + isp->isp_dblev |= ISP_LOGCONFIG|ISP_LOGINFO; + } + +#ifdef ISP_FW_CRASH_DUMP + bitmap = 0; + if (getenv_int("isp_fw_dump_enable", &bitmap)) { + if (bitmap & (1 << unit) { + size_t amt = 0; + if (IS_2200(isp)) { + amt = QLA2200_RISC_IMAGE_DUMP_SIZE; + } else if (IS_23XX(isp)) { + amt = QLA2300_RISC_IMAGE_DUMP_SIZE; + } + if (amt) { + FCPARAM(isp)->isp_dump_data = + malloc(amt, M_DEVBUF, M_WAITOK); + bzero(FCPARAM(isp)->isp_dump_data, amt); + } else { + device_printf(dev, + "f/w crash dumps not supported for card\n"); + } + } + } +#endif +} + +static void +isp_get_pci_options(device_t dev, int *m1, int *m2) +{ + int bitmap; + int unit = device_get_unit(dev); + + *m1 = PCIM_CMD_MEMEN; + *m2 = PCIM_CMD_PORTEN; + if (getenv_int("isp_mem_map", &bitmap)) { + if (bitmap & (1 << unit)) { + *m1 = PCIM_CMD_MEMEN; + *m2 = PCIM_CMD_PORTEN; + } + } + bitmap = 0; + if (getenv_int("isp_io_map", &bitmap)) { + if (bitmap & (1 << unit)) { + *m1 = PCIM_CMD_PORTEN; + *m2 = PCIM_CMD_MEMEN; + } + } +} +#else +static void +isp_get_options(device_t dev, ispsoftc_t *isp) +{ + int tval; + const char *sptr; + /* * Figure out if we're supposed to skip this one. */ tval = 0; if (resource_int_value(device_get_name(dev), device_get_unit(dev), "disable", &tval) == 0 && tval) { - device_printf(dev, "device is disabled\n"); - /* but return 0 so the !$)$)*!$*) unit isn't reused */ - return (0); + device_printf(dev, "disabled at user request\n"); + isp->isp_osinfo.disabled = 1; + return; } - role = -1; + tval = -1; if (resource_int_value(device_get_name(dev), device_get_unit(dev), - "role", &role) == 0 && role != -1) { - role &= (ISP_ROLE_INITIATOR|ISP_ROLE_TARGET); - device_printf(dev, "setting role to 0x%x\n", role); + "role", &tval) == 0 && tval != -1) { + tval &= (ISP_ROLE_INITIATOR|ISP_ROLE_TARGET); + isp->isp_role = tval; + device_printf(dev, "setting role to 0x%x\n", isp->isp_role); } else { #ifdef ISP_TARGET_MODE - role = ISP_ROLE_TARGET; + isp->isp_role = ISP_ROLE_TARGET; #else - role = ISP_DEFAULT_ROLES; + isp->isp_role = ISP_DEFAULT_ROLES; #endif } - pcs = malloc(sizeof (struct isp_pcisoftc), M_DEVBUF, M_NOWAIT | M_ZERO); - if (pcs == NULL) { - device_printf(dev, "cannot allocate softc\n"); - return (ENOMEM); + tval = 0; + if (resource_int_value(device_get_name(dev), device_get_unit(dev), + "fwload_disable", &tval) == 0 && tval != 0) { + isp->isp_confopts |= ISP_CFG_NORELOAD; + } + tval = 0; + if (resource_int_value(device_get_name(dev), device_get_unit(dev), + "ignore_nvram", &tval) == 0 && tval != 0) { + isp->isp_confopts |= ISP_CFG_NONVRAM; + } + tval = 0; + if (resource_int_value(device_get_name(dev), device_get_unit(dev), + "fullduplex", &tval) == 0 && tval != 0) { + isp->isp_confopts |= ISP_CFG_FULL_DUPLEX; + } +#ifdef ISP_FW_CRASH_DUMP + tval = 0; + if (resource_int_value(device_get_name(dev), device_get_unit(dev), + "fw_dump_enable", &tval) == 0 && tval != 0) { + size_t amt = 0; + if (IS_2200(isp)) { + amt = QLA2200_RISC_IMAGE_DUMP_SIZE; + } else if (IS_23XX(isp)) { + amt = QLA2300_RISC_IMAGE_DUMP_SIZE; + } + if (amt) { + FCPARAM(isp)->isp_dump_data = + malloc(amt, M_DEVBUF, M_WAITOK | M_ZERO); + } else { + device_printf(dev, + "f/w crash dumps not supported for this model\n"); + } + } +#endif + + sptr = 0; + if (resource_string_value(device_get_name(dev), device_get_unit(dev), + "topology", (const char **) &sptr) == 0 && sptr != 0) { + if (strcmp(sptr, "lport") == 0) { + isp->isp_confopts |= ISP_CFG_LPORT; + } else if (strcmp(sptr, "nport") == 0) { + isp->isp_confopts |= ISP_CFG_NPORT; + } else if (strcmp(sptr, "lport-only") == 0) { + isp->isp_confopts |= ISP_CFG_LPORT_ONLY; + } else if (strcmp(sptr, "nport-only") == 0) { + isp->isp_confopts |= ISP_CFG_NPORT_ONLY; + } + } + + /* + * Because the resource_*_value functions can neither return + * 64 bit integer values, nor can they be directly coerced + * to interpret the right hand side of the assignment as + * you want them to interpret it, we have to force WWN + * hint replacement to specify WWN strings with a leading + * 'w' (e..g w50000000aaaa0001). Sigh. + */ + sptr = 0; + tval = resource_string_value(device_get_name(dev), device_get_unit(dev), + "portwwn", (const char **) &sptr); + if (tval == 0 && sptr != 0 && *sptr++ == 'w') { + char *eptr = 0; + isp->isp_osinfo.default_port_wwn = strtouq(sptr, &eptr, 16); + if (eptr < sptr + 16 || isp->isp_osinfo.default_port_wwn == 0) { + device_printf(dev, "mangled portwwn hint '%s'\n", sptr); + isp->isp_osinfo.default_port_wwn = 0; + } else { + isp->isp_confopts |= ISP_CFG_OWNWWPN; + } + } + if (isp->isp_osinfo.default_port_wwn == 0) { + isp->isp_osinfo.default_port_wwn = 0x400000007F000009ull; + } + + sptr = 0; + tval = resource_string_value(device_get_name(dev), device_get_unit(dev), + "nodewwn", (const char **) &sptr); + if (tval == 0 && sptr != 0 && *sptr++ == 'w') { + char *eptr = 0; + isp->isp_osinfo.default_node_wwn = strtouq(sptr, &eptr, 16); + if (eptr < sptr + 16 || isp->isp_osinfo.default_node_wwn == 0) { + device_printf(dev, "mangled nodewwn hint '%s'\n", sptr); + isp->isp_osinfo.default_node_wwn = 0; + } else { + isp->isp_confopts |= ISP_CFG_OWNWWNN; + } + } + if (isp->isp_osinfo.default_node_wwn == 0) { + isp->isp_osinfo.default_node_wwn = 0x400000007F000009ull; + } + + isp->isp_osinfo.default_id = -1; + if (resource_int_value(device_get_name(dev), device_get_unit(dev), + "iid", &tval) == 0) { + isp->isp_osinfo.default_id = tval; + isp->isp_confopts |= ISP_CFG_OWNLOOPID; + } + if (isp->isp_osinfo.default_id == -1) { + if (IS_FC(isp)) { + isp->isp_osinfo.default_id = 109; + } else { + isp->isp_osinfo.default_id = 7; + } } /* + * Set up logging levels. + */ + tval = 0; + (void) resource_int_value(device_get_name(dev), device_get_unit(dev), + "debug", &tval); + if (tval) { + isp->isp_dblev = tval; + } else { + isp->isp_dblev = ISP_LOGWARN|ISP_LOGERR; + } + if (bootverbose) { + isp->isp_dblev |= ISP_LOGCONFIG|ISP_LOGINFO; + } + +} + +static void +isp_get_pci_options(device_t dev, int *m1, int *m2) +{ + int tval; + /* * Which we should try first - memory mapping or i/o mapping? * * We used to try memory first followed by i/o on alpha, otherwise * the reverse, but we should just try memory first all the time now. */ - m1 = PCIM_CMD_MEMEN; - m2 = PCIM_CMD_PORTEN; + *m1 = PCIM_CMD_MEMEN; + *m2 = PCIM_CMD_PORTEN; tval = 0; if (resource_int_value(device_get_name(dev), device_get_unit(dev), "prefer_iomap", &tval) == 0 && tval != 0) { - m1 = PCIM_CMD_PORTEN; - m2 = PCIM_CMD_MEMEN; + *m1 = PCIM_CMD_PORTEN; + *m2 = PCIM_CMD_MEMEN; } tval = 0; if (resource_int_value(device_get_name(dev), device_get_unit(dev), "prefer_memmap", &tval) == 0 && tval != 0) { - m1 = PCIM_CMD_MEMEN; - m2 = PCIM_CMD_PORTEN; + *m1 = PCIM_CMD_MEMEN; + *m2 = PCIM_CMD_PORTEN; + } +} +#endif + +static int +isp_pci_attach(device_t dev) +{ + struct resource *regs, *irq; + int rtp, rgd, iqd, m1, m2; + uint32_t data, cmd, linesz, psize, basetype; + struct isp_pcisoftc *pcs; + ispsoftc_t *isp = NULL; + struct ispmdvec *mdvp; +#if __FreeBSD_version >= 500000 + int locksetup = 0; +#endif + + pcs = device_get_softc(dev); + if (pcs == NULL) { + device_printf(dev, "cannot get softc\n"); + return (ENOMEM); } + memset(pcs, 0, sizeof (*pcs)); + pcs->pci_dev = dev; + isp = &pcs->pci_isp; + + /* + * Get Generic Options + */ + isp_get_options(dev, isp); + + /* + * Check to see if options have us disabled + */ + if (isp->isp_osinfo.disabled) { + /* + * But return zero to preserve unit numbering + */ + return (0); + } + + /* + * Get PCI options- which in this case are just mapping preferences. + */ + isp_get_pci_options(dev, &m1, &m2); + linesz = PCI_DFLT_LNSZ; irq = regs = NULL; @@ -456,9 +750,10 @@ isp_pci_attach(device_t dev) device_printf(dev, "unable to map any ports\n"); goto bad; } - if (bootverbose) + if (bootverbose) { device_printf(dev, "using %s space register mapping\n", (rgd == IO_MAP_REG)? "I/O" : "Memory"); + } pcs->pci_dev = dev; pcs->pci_reg = regs; pcs->pci_st = rman_get_bustag(regs); @@ -573,7 +868,6 @@ isp_pci_attach(device_t dev) isp->isp_mdvec = mdvp; isp->isp_type = basetype; isp->isp_revision = pci_get_revid(dev); - isp->isp_role = role; isp->isp_dev = dev; /* @@ -645,118 +939,11 @@ isp_pci_attach(device_t dev) goto bad; } - tval = 0; - if (resource_int_value(device_get_name(dev), device_get_unit(dev), - "fwload_disable", &tval) == 0 && tval != 0) { - isp->isp_confopts |= ISP_CFG_NORELOAD; - } - tval = 0; - if (resource_int_value(device_get_name(dev), device_get_unit(dev), - "ignore_nvram", &tval) == 0 && tval != 0) { - isp->isp_confopts |= ISP_CFG_NONVRAM; - } - tval = 0; - if (resource_int_value(device_get_name(dev), device_get_unit(dev), - "fullduplex", &tval) == 0 && tval != 0) { - isp->isp_confopts |= ISP_CFG_FULL_DUPLEX; - } -#ifdef ISP_FW_CRASH_DUMP - tval = 0; - if (resource_int_value(device_get_name(dev), device_get_unit(dev), - "fw_dump_enable", &tval) == 0 && tval != 0) { - size_t amt = 0; - if (IS_2200(isp)) { - amt = QLA2200_RISC_IMAGE_DUMP_SIZE; - } else if (IS_23XX(isp)) { - amt = QLA2300_RISC_IMAGE_DUMP_SIZE; - } - if (amt) { - FCPARAM(isp)->isp_dump_data = - malloc(amt, M_DEVBUF, M_WAITOK | M_ZERO); - } else { - device_printf(dev, - "f/w crash dumps not supported for this model\n"); - } - } -#endif - - sptr = 0; - if (resource_string_value(device_get_name(dev), device_get_unit(dev), - "topology", (const char **) &sptr) == 0 && sptr != 0) { - if (strcmp(sptr, "lport") == 0) { - isp->isp_confopts |= ISP_CFG_LPORT; - } else if (strcmp(sptr, "nport") == 0) { - isp->isp_confopts |= ISP_CFG_NPORT; - } else if (strcmp(sptr, "lport-only") == 0) { - isp->isp_confopts |= ISP_CFG_LPORT_ONLY; - } else if (strcmp(sptr, "nport-only") == 0) { - isp->isp_confopts |= ISP_CFG_NPORT_ONLY; - } - } - - /* - * Because the resource_*_value functions can neither return - * 64 bit integer values, nor can they be directly coerced - * to interpret the right hand side of the assignment as - * you want them to interpret it, we have to force WWN - * hint replacement to specify WWN strings with a leading - * 'w' (e..g w50000000aaaa0001). Sigh. - */ - sptr = 0; - tval = resource_string_value(device_get_name(dev), device_get_unit(dev), - "portwwn", (const char **) &sptr); - if (tval == 0 && sptr != 0 && *sptr++ == 'w') { - char *eptr = 0; - isp->isp_osinfo.default_port_wwn = strtouq(sptr, &eptr, 16); - if (eptr < sptr + 16 || isp->isp_osinfo.default_port_wwn == 0) { - device_printf(dev, "mangled portwwn hint '%s'\n", sptr); - isp->isp_osinfo.default_port_wwn = 0; - } else { - isp->isp_confopts |= ISP_CFG_OWNWWPN; - } - } - if (isp->isp_osinfo.default_port_wwn == 0) { - isp->isp_osinfo.default_port_wwn = 0x400000007F000009ull; - } - - sptr = 0; - tval = resource_string_value(device_get_name(dev), device_get_unit(dev), - "nodewwn", (const char **) &sptr); - if (tval == 0 && sptr != 0 && *sptr++ == 'w') { - char *eptr = 0; - isp->isp_osinfo.default_node_wwn = strtouq(sptr, &eptr, 16); - if (eptr < sptr + 16 || isp->isp_osinfo.default_node_wwn == 0) { - device_printf(dev, "mangled nodewwn hint '%s'\n", sptr); - isp->isp_osinfo.default_node_wwn = 0; - } else { - isp->isp_confopts |= ISP_CFG_OWNWWNN; - } - } - if (isp->isp_osinfo.default_node_wwn == 0) { - isp->isp_osinfo.default_node_wwn = 0x400000007F000009ull; - } - - isp->isp_osinfo.default_id = -1; - if (resource_int_value(device_get_name(dev), device_get_unit(dev), - "iid", &tval) == 0) { - isp->isp_osinfo.default_id = tval; - isp->isp_confopts |= ISP_CFG_OWNLOOPID; - } - if (isp->isp_osinfo.default_id == -1) { - if (IS_FC(isp)) { - isp->isp_osinfo.default_id = 109; - } else { - isp->isp_osinfo.default_id = 7; - } - } - - isp_debug = 0; - (void) resource_int_value(device_get_name(dev), device_get_unit(dev), - "debug", &isp_debug); - +#if __FreeBSD_version >= 500000 /* Make sure the lock is set up. */ mtx_init(&isp->isp_osinfo.lock, "isp", NULL, MTX_DEF); locksetup++; +#endif if (bus_setup_intr(dev, irq, ISP_IFLAGS, isp_pci_intr, isp, &pcs->ih)) { device_printf(dev, "could not setup interrupt\n"); @@ -764,17 +951,6 @@ isp_pci_attach(device_t dev) } /* - * Set up logging levels. - */ - if (isp_debug) { - isp->isp_dblev = isp_debug; - } else { - isp->isp_dblev = ISP_LOGWARN|ISP_LOGERR; - } - if (bootverbose) - isp->isp_dblev |= ISP_LOGCONFIG|ISP_LOGINFO; - - /* * Last minute checks... */ if (IS_23XX(isp)) { @@ -815,9 +991,11 @@ bad: (void) bus_teardown_intr(dev, irq, pcs->ih); } +#if __FreeBSD_version >= 500000 if (locksetup && isp) { mtx_destroy(&isp->isp_osinfo.lock); } +#endif if (irq) { (void) bus_release_resource(dev, SYS_RES_IRQ, iqd, irq); @@ -829,9 +1007,14 @@ bad: } if (pcs) { - if (pcs->pci_isp.isp_param) + if (pcs->pci_isp.isp_param) { +#ifdef ISP_FW_CRASH_DUMP + if (IS_FC(isp) && FCPARAM(isp)->isp_dump_data) { + free(FCPARAM(isp)->isp_dump_data, M_DEVBUF); + } +#endif free(pcs->pci_isp.isp_param, M_DEVBUF); - free(pcs, M_DEVBUF); + } } /* @@ -844,7 +1027,7 @@ bad: static void isp_pci_intr(void *arg) { - struct ispsoftc *isp = arg; + ispsoftc_t *isp = arg; uint16_t isr, sema, mbox; ISP_LOCK(isp); @@ -872,7 +1055,7 @@ isp_pci_intr(void *arg) static __inline int -isp_pci_rd_debounced(struct ispsoftc *isp, int off, uint16_t *rp) +isp_pci_rd_debounced(ispsoftc_t *isp, int off, uint16_t *rp) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *) isp; uint16_t val0, val1; @@ -890,7 +1073,7 @@ isp_pci_rd_debounced(struct ispsoftc *isp, int off, uint16_t *rp) } static int -isp_pci_rd_isr(struct ispsoftc *isp, uint16_t *isrp, +isp_pci_rd_isr(ispsoftc_t *isp, uint16_t *isrp, uint16_t *semap, uint16_t *mbp) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *) isp; @@ -927,7 +1110,7 @@ isp_pci_rd_isr(struct ispsoftc *isp, uint16_t *isrp, } static int -isp_pci_rd_isr_2300(struct ispsoftc *isp, uint16_t *isrp, +isp_pci_rd_isr_2300(ispsoftc_t *isp, uint16_t *isrp, uint16_t *semap, uint16_t *mbox0p) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *) isp; @@ -980,7 +1163,7 @@ isp_pci_rd_isr_2300(struct ispsoftc *isp, uint16_t *isrp, } static uint16_t -isp_pci_rd_reg(struct ispsoftc *isp, int regoff) +isp_pci_rd_reg(ispsoftc_t *isp, int regoff) { uint16_t rv; struct isp_pcisoftc *pcs = (struct isp_pcisoftc *) isp; @@ -1002,7 +1185,7 @@ isp_pci_rd_reg(struct ispsoftc *isp, int regoff) } static void -isp_pci_wr_reg(struct ispsoftc *isp, int regoff, uint16_t val) +isp_pci_wr_reg(ispsoftc_t *isp, int regoff, uint16_t val) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *) isp; int oldconf = 0; @@ -1022,7 +1205,7 @@ isp_pci_wr_reg(struct ispsoftc *isp, int regoff, uint16_t val) } static uint16_t -isp_pci_rd_reg_1080(struct ispsoftc *isp, int regoff) +isp_pci_rd_reg_1080(ispsoftc_t *isp, int regoff) { uint16_t rv, oc = 0; struct isp_pcisoftc *pcs = (struct isp_pcisoftc *) isp; @@ -1053,7 +1236,7 @@ isp_pci_rd_reg_1080(struct ispsoftc *isp, int regoff) } static void -isp_pci_wr_reg_1080(struct ispsoftc *isp, int regoff, uint16_t val) +isp_pci_wr_reg_1080(ispsoftc_t *isp, int regoff, uint16_t val) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *) isp; int oc = 0; @@ -1084,7 +1267,7 @@ isp_pci_wr_reg_1080(struct ispsoftc *isp, int regoff, uint16_t val) struct imush { - struct ispsoftc *isp; + ispsoftc_t *isp; int error; }; @@ -1097,7 +1280,7 @@ imc(void *arg, bus_dma_segment_t *segs, int nseg, int error) if (error) { imushp->error = error; } else { - struct ispsoftc *isp =imushp->isp; + ispsoftc_t *isp =imushp->isp; bus_addr_t addr = segs->ds_addr; isp->isp_rquest_dma = addr; @@ -1115,8 +1298,16 @@ imc(void *arg, bus_dma_segment_t *segs, int nseg, int error) */ #define ISP_NSEGS ((MAXPHYS / PAGE_SIZE) + 1) +#if __FreeBSD_version < 500000 +#define isp_dma_tag_create bus_dma_tag_create +#else +#define isp_dma_tag_create(a, b, c, d, e, f, g, h, i, j, k, z) \ + bus_dma_tag_create(a, b, c, d, e, f, g, h, i, j, k, \ + busdma_lock_mutex, &Giant, z) +#endif + static int -isp_pci_mbxdma(struct ispsoftc *isp) +isp_pci_mbxdma(ispsoftc_t *isp) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *)isp; caddr_t base; @@ -1151,9 +1342,8 @@ isp_pci_mbxdma(struct ispsoftc *isp) } ISP_UNLOCK(isp); - if (bus_dma_tag_create(NULL, 1, slim, llim, hlim, - NULL, NULL, BUS_SPACE_MAXSIZE, ISP_NSEGS, slim, 0, - busdma_lock_mutex, &Giant, &pcs->dmat)) { + if (isp_dma_tag_create(NULL, 1, slim, llim, hlim, + NULL, NULL, BUS_SPACE_MAXSIZE, ISP_NSEGS, slim, 0, &pcs->dmat)) { isp_prt(isp, ISP_LOGERR, "could not create master dma tag"); ISP_LOCK(isp); return(1); @@ -1201,10 +1391,9 @@ isp_pci_mbxdma(struct ispsoftc *isp) /* * Create a tag for the control spaces- force it to within 32 bits. */ - if (bus_dma_tag_create(pcs->dmat, QENTRY_LEN, slim, + if (isp_dma_tag_create(pcs->dmat, QENTRY_LEN, slim, BUS_SPACE_MAXADDR_32BIT, BUS_SPACE_MAXADDR, - NULL, NULL, len, ns, slim, 0, busdma_lock_mutex, &Giant, - &isp->isp_cdmat)) { + NULL, NULL, len, ns, slim, 0, &isp->isp_cdmat)) { isp_prt(isp, ISP_LOGERR, "cannot create a dma tag for control spaces"); free(pcs->dmaps, M_DEVBUF); @@ -1275,7 +1464,7 @@ bad: } typedef struct { - struct ispsoftc *isp; + ispsoftc_t *isp; void *cmd_token; void *rq; uint16_t *nxtip; @@ -1312,7 +1501,7 @@ tdma_mk(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) { mush_t *mp; struct ccb_scsiio *csio; - struct ispsoftc *isp; + ispsoftc_t *isp; struct isp_pcisoftc *pcs; bus_dmamap_t *dp; ct_entry_t *cto, *qe; @@ -1555,7 +1744,7 @@ tdma_mkfc(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) { mush_t *mp; struct ccb_scsiio *csio; - struct ispsoftc *isp; + ispsoftc_t *isp; ct2_entry_t *cto, *qe; uint16_t curi, nxti; int segcnt; @@ -1620,10 +1809,17 @@ tdma_mkfc(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) cto->rsp.m0.ct_dataseg[cto->ct_seg_count].ds_count = dm_segs[segcnt].ds_len; cto->rsp.m0.ct_xfrlen += dm_segs[segcnt].ds_len; +#if __FreeBSD_version < 500000 + isp_prt(isp, ISP_LOGTDEBUG1, + "isp_send_ctio2: ent0[%d]0x%llx:%llu", + cto->ct_seg_count, (uint64_t)dm_segs[segcnt].ds_addr, + (uint64_t)dm_segs[segcnt].ds_len); +#else isp_prt(isp, ISP_LOGTDEBUG1, "isp_send_ctio2: ent0[%d]0x%jx:%ju", cto->ct_seg_count, (uintmax_t)dm_segs[segcnt].ds_addr, (uintmax_t)dm_segs[segcnt].ds_len); +#endif } while (segcnt < nseg) { @@ -1649,11 +1845,19 @@ tdma_mkfc(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) segcnt++, seg++) { crq->req_dataseg[seg].ds_base = dm_segs[segcnt].ds_addr; crq->req_dataseg[seg].ds_count = dm_segs[segcnt].ds_len; +#if __FreeBSD_version < 500000 + isp_prt(isp, ISP_LOGTDEBUG1, + "isp_send_ctio2: ent%d[%d]%llx:%llu", + cto->ct_header.rqs_entry_count-1, seg, + (uint64_t)dm_segs[segcnt].ds_addr, + (uint64_t)dm_segs[segcnt].ds_len); +#else isp_prt(isp, ISP_LOGTDEBUG1, "isp_send_ctio2: ent%d[%d]%jx:%ju", cto->ct_header.rqs_entry_count-1, seg, (uintmax_t)dm_segs[segcnt].ds_addr, (uintmax_t)dm_segs[segcnt].ds_len); +#endif cto->rsp.m0.ct_xfrlen += dm_segs[segcnt].ds_len; cto->ct_seg_count++; } @@ -1684,7 +1888,7 @@ static void dma2_a64(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) { mush_t *mp; - struct ispsoftc *isp; + ispsoftc_t *isp; struct ccb_scsiio *csio; struct isp_pcisoftc *pcs; bus_dmamap_t *dp; @@ -1815,7 +2019,7 @@ static void dma2(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) { mush_t *mp; - struct ispsoftc *isp; + ispsoftc_t *isp; struct ccb_scsiio *csio; struct isp_pcisoftc *pcs; bus_dmamap_t *dp; @@ -1935,8 +2139,11 @@ dma2(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) *mp->nxtip = nxti; } +/* + * We enter with ISP_LOCK held + */ static int -isp_pci_dmasetup(struct ispsoftc *isp, struct ccb_scsiio *csio, ispreq_t *rq, +isp_pci_dmasetup(ispsoftc_t *isp, struct ccb_scsiio *csio, ispreq_t *rq, uint16_t *nxtip, uint16_t optr) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *)isp; @@ -1962,7 +2169,9 @@ isp_pci_dmasetup(struct ispsoftc *isp, struct ccb_scsiio *csio, ispreq_t *rq, mp->nxtip = nxtip; mp->optr = optr; mp->error = 0; + ISPLOCK_2_CAMLOCK(isp); (*eptr)(mp, NULL, 0, 0); + CAMLOCK_2_ISPLOCK(isp); goto mbxsync; } } else @@ -1992,6 +2201,7 @@ isp_pci_dmasetup(struct ispsoftc *isp, struct ccb_scsiio *csio, ispreq_t *rq, mp->optr = optr; mp->error = 0; + ISPLOCK_2_CAMLOCK(isp); if ((csio->ccb_h.flags & CAM_SCATTER_VALID) == 0) { if ((csio->ccb_h.flags & CAM_DATA_PHYS) == 0) { int error, s; @@ -2036,6 +2246,7 @@ isp_pci_dmasetup(struct ispsoftc *isp, struct ccb_scsiio *csio, ispreq_t *rq, (*eptr)(mp, segs, csio->sglist_cnt, 0); } } + CAMLOCK_2_ISPLOCK(isp); if (mp->error) { int retval = CMD_COMPLETE; if (mp->error == MUSHERR_NOQENTRIES) { @@ -2070,7 +2281,7 @@ mbxsync: } static void -isp_pci_dmateardown(struct ispsoftc *isp, XS_T *xs, uint16_t handle) +isp_pci_dmateardown(ispsoftc_t *isp, XS_T *xs, uint16_t handle) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *)isp; bus_dmamap_t *dp = &pcs->dmaps[isp_handle_index(handle)]; @@ -2084,7 +2295,7 @@ isp_pci_dmateardown(struct ispsoftc *isp, XS_T *xs, uint16_t handle) static void -isp_pci_reset1(struct ispsoftc *isp) +isp_pci_reset1(ispsoftc_t *isp) { /* Make sure the BIOS is disabled */ isp_pci_wr_reg(isp, HCCR, PCI_HCCR_CMD_BIOS); @@ -2093,7 +2304,7 @@ isp_pci_reset1(struct ispsoftc *isp) } static void -isp_pci_dumpregs(struct ispsoftc *isp, const char *msg) +isp_pci_dumpregs(ispsoftc_t *isp, const char *msg) { struct isp_pcisoftc *pcs = (struct isp_pcisoftc *)isp; if (msg) diff --git a/sys/dev/isp/isp_sbus.c b/sys/dev/isp/isp_sbus.c index 91b99edf83c05..dc05871f4fcc6 100644 --- a/sys/dev/isp/isp_sbus.c +++ b/sys/dev/isp/isp_sbus.c @@ -46,18 +46,18 @@ __FBSDID("$FreeBSD$"); #include <dev/isp/isp_freebsd.h> -static uint16_t isp_sbus_rd_reg(struct ispsoftc *, int); -static void isp_sbus_wr_reg(struct ispsoftc *, int, uint16_t); +static uint16_t isp_sbus_rd_reg(ispsoftc_t *, int); +static void isp_sbus_wr_reg(ispsoftc_t *, int, uint16_t); static int -isp_sbus_rd_isr(struct ispsoftc *, uint16_t *, uint16_t *, uint16_t *); -static int isp_sbus_mbxdma(struct ispsoftc *); +isp_sbus_rd_isr(ispsoftc_t *, uint16_t *, uint16_t *, uint16_t *); +static int isp_sbus_mbxdma(ispsoftc_t *); static int -isp_sbus_dmasetup(struct ispsoftc *, XS_T *, ispreq_t *, uint16_t *, uint16_t); +isp_sbus_dmasetup(ispsoftc_t *, XS_T *, ispreq_t *, uint16_t *, uint16_t); static void -isp_sbus_dmateardown(struct ispsoftc *, XS_T *, uint16_t); +isp_sbus_dmateardown(ispsoftc_t *, XS_T *, uint16_t); -static void isp_sbus_reset1(struct ispsoftc *); -static void isp_sbus_dumpregs(struct ispsoftc *, const char *); +static void isp_sbus_reset1(ispsoftc_t *); +static void isp_sbus_dumpregs(ispsoftc_t *, const char *); static struct ispmdvec mdvec = { isp_sbus_rd_isr, @@ -78,7 +78,7 @@ static int isp_sbus_attach (device_t); struct isp_sbussoftc { - struct ispsoftc sbus_isp; + ispsoftc_t sbus_isp; device_t sbus_dev; struct resource * sbus_reg; bus_space_tag_t sbus_st; @@ -138,7 +138,7 @@ isp_sbus_attach(device_t dev) struct resource *regs; int tval, iqd, isp_debug, role, rid, ispburst; struct isp_sbussoftc *sbs; - struct ispsoftc *isp = NULL; + ispsoftc_t *isp = NULL; int locksetup = 0; /* @@ -373,7 +373,7 @@ bad: static void isp_sbus_intr(void *arg) { - struct ispsoftc *isp = arg; + ispsoftc_t *isp = arg; uint16_t isr, sema, mbox; ISP_LOCK(isp); @@ -397,7 +397,7 @@ isp_sbus_intr(void *arg) bus_space_read_2(sbc->sbus_st, sbc->sbus_sh, off) static int -isp_sbus_rd_isr(struct ispsoftc *isp, uint16_t *isrp, +isp_sbus_rd_isr(ispsoftc_t *isp, uint16_t *isrp, uint16_t *semap, uint16_t *mbp) { struct isp_sbussoftc *sbc = (struct isp_sbussoftc *) isp; @@ -419,7 +419,7 @@ isp_sbus_rd_isr(struct ispsoftc *isp, uint16_t *isrp, } static uint16_t -isp_sbus_rd_reg(struct ispsoftc *isp, int regoff) +isp_sbus_rd_reg(ispsoftc_t *isp, int regoff) { uint16_t rval; struct isp_sbussoftc *sbs = (struct isp_sbussoftc *) isp; @@ -432,7 +432,7 @@ isp_sbus_rd_reg(struct ispsoftc *isp, int regoff) } static void -isp_sbus_wr_reg(struct ispsoftc *isp, int regoff, uint16_t val) +isp_sbus_wr_reg(ispsoftc_t *isp, int regoff, uint16_t val) { struct isp_sbussoftc *sbs = (struct isp_sbussoftc *) isp; int offset = sbs->sbus_poff[(regoff & _BLK_REG_MASK) >> _BLK_REG_SHFT]; @@ -443,7 +443,7 @@ isp_sbus_wr_reg(struct ispsoftc *isp, int regoff, uint16_t val) } struct imush { - struct ispsoftc *isp; + ispsoftc_t *isp; int error; }; @@ -456,7 +456,7 @@ imc(void *arg, bus_dma_segment_t *segs, int nseg, int error) if (error) { imushp->error = error; } else { - struct ispsoftc *isp =imushp->isp; + ispsoftc_t *isp =imushp->isp; bus_addr_t addr = segs->ds_addr; isp->isp_rquest_dma = addr; @@ -471,7 +471,7 @@ imc(void *arg, bus_dma_segment_t *segs, int nseg, int error) #define ISP_NSEGS ((MAXPHYS / PAGE_SIZE) + 1) static int -isp_sbus_mbxdma(struct ispsoftc *isp) +isp_sbus_mbxdma(ispsoftc_t *isp) { struct isp_sbussoftc *sbs = (struct isp_sbussoftc *)isp; caddr_t base; @@ -582,7 +582,7 @@ bad: } typedef struct { - struct ispsoftc *isp; + ispsoftc_t *isp; void *cmd_token; void *rq; uint16_t *nxtip; @@ -599,7 +599,7 @@ static void dma2(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) { mush_t *mp; - struct ispsoftc *isp; + ispsoftc_t *isp; struct ccb_scsiio *csio; struct isp_sbussoftc *sbs; bus_dmamap_t *dp; @@ -700,7 +700,7 @@ dma2(void *arg, bus_dma_segment_t *dm_segs, int nseg, int error) } static int -isp_sbus_dmasetup(struct ispsoftc *isp, struct ccb_scsiio *csio, ispreq_t *rq, +isp_sbus_dmasetup(ispsoftc_t *isp, struct ccb_scsiio *csio, ispreq_t *rq, uint16_t *nxtip, uint16_t optr) { struct isp_sbussoftc *sbs = (struct isp_sbussoftc *)isp; @@ -802,7 +802,7 @@ mbxsync: } static void -isp_sbus_dmateardown(struct ispsoftc *isp, XS_T *xs, uint16_t handle) +isp_sbus_dmateardown(ispsoftc_t *isp, XS_T *xs, uint16_t handle) { struct isp_sbussoftc *sbs = (struct isp_sbussoftc *)isp; bus_dmamap_t *dp = &sbs->dmaps[isp_handle_index(handle)]; @@ -816,14 +816,14 @@ isp_sbus_dmateardown(struct ispsoftc *isp, XS_T *xs, uint16_t handle) static void -isp_sbus_reset1(struct ispsoftc *isp) +isp_sbus_reset1(ispsoftc_t *isp) { /* enable interrupts */ ENABLE_INTS(isp); } static void -isp_sbus_dumpregs(struct ispsoftc *isp, const char *msg) +isp_sbus_dumpregs(ispsoftc_t *isp, const char *msg) { if (msg) printf("%s: %s\n", device_get_nameunit(isp->isp_dev), msg); diff --git a/sys/dev/isp/isp_target.c b/sys/dev/isp/isp_target.c index 42c70cc677842..4ddcc9290ac4a 100644 --- a/sys/dev/isp/isp_target.c +++ b/sys/dev/isp/isp_target.c @@ -59,12 +59,12 @@ static const char atior[] = "ATIO returned on for lun %d on from IID %d because a Bus Reset occurred " "on bus %d"; -static void isp_got_msg(struct ispsoftc *, in_entry_t *); -static void isp_got_msg_fc(struct ispsoftc *, in_fcentry_t *); -static void isp_handle_atio(struct ispsoftc *, at_entry_t *); -static void isp_handle_atio2(struct ispsoftc *, at2_entry_t *); -static void isp_handle_ctio(struct ispsoftc *, ct_entry_t *); -static void isp_handle_ctio2(struct ispsoftc *, ct2_entry_t *); +static void isp_got_msg(ispsoftc_t *, in_entry_t *); +static void isp_got_msg_fc(ispsoftc_t *, in_fcentry_t *); +static void isp_handle_atio(ispsoftc_t *, at_entry_t *); +static void isp_handle_atio2(ispsoftc_t *, at2_entry_t *); +static void isp_handle_ctio(ispsoftc_t *, ct_entry_t *); +static void isp_handle_ctio2(ispsoftc_t *, ct2_entry_t *); /* * The Qlogic driver gets an interrupt to look at response queue entries. @@ -113,7 +113,7 @@ static void isp_handle_ctio2(struct ispsoftc *, ct2_entry_t *); */ int -isp_target_notify(struct ispsoftc *isp, void *vptr, uint16_t *optrp) +isp_target_notify(ispsoftc_t *isp, void *vptr, uint16_t *optrp) { uint16_t status, seqid; union { @@ -303,7 +303,7 @@ isp_target_notify(struct ispsoftc *isp, void *vptr, uint16_t *optrp) * response entry. The caller is responsible for synchronizing this. */ int -isp_lun_cmd(struct ispsoftc *isp, int cmd, int bus, int tgt, int lun, +isp_lun_cmd(ispsoftc_t *isp, int cmd, int bus, int tgt, int lun, int cmd_cnt, int inot_cnt, uint32_t opaque) { lun_entry_t el; @@ -342,7 +342,6 @@ isp_lun_cmd(struct ispsoftc *isp, int cmd, int bus, int tgt, int lun, } else if ((FCPARAM(isp)->isp_fwattr & ISP_FW_ATTR_SCCLUN) == 0) { el.le_lun = lun; } - el.le_timeout = 2; if (isp_getrqentry(isp, &nxti, &optr, &outp)) { isp_prt(isp, ISP_LOGERR, @@ -357,7 +356,7 @@ isp_lun_cmd(struct ispsoftc *isp, int cmd, int bus, int tgt, int lun, int -isp_target_put_entry(struct ispsoftc *isp, void *ap) +isp_target_put_entry(ispsoftc_t *isp, void *ap) { void *outp; uint16_t nxti, optr; @@ -393,7 +392,7 @@ isp_target_put_entry(struct ispsoftc *isp, void *ap) } int -isp_target_put_atio(struct ispsoftc *isp, void *arg) +isp_target_put_atio(ispsoftc_t *isp, void *arg) { union { at_entry_t _atio; @@ -453,7 +452,7 @@ isp_target_put_atio(struct ispsoftc *isp, void *arg) */ int -isp_endcmd(struct ispsoftc *isp, void *arg, uint32_t code, uint16_t hdl) +isp_endcmd(ispsoftc_t *isp, void *arg, uint32_t code, uint16_t hdl) { int sts; union { @@ -524,14 +523,16 @@ isp_endcmd(struct ispsoftc *isp, void *arg, uint32_t code, uint16_t hdl) return (isp_target_put_entry(isp, &un)); } +/* + * These are either broadcast events or specifically CTIO fast completion + */ int -isp_target_async(struct ispsoftc *isp, int bus, int event) +isp_target_async(ispsoftc_t *isp, int bus, int event) { tmd_notify_t notify; MEMZERO(¬ify, sizeof (tmd_notify_t)); notify.nt_hba = isp; - /* nt_str set in outer layers */ notify.nt_iid = INI_ANY; /* nt_tgt set in outer layers */ notify.nt_lun = LUN_ANY; @@ -607,14 +608,13 @@ isp_target_async(struct ispsoftc *isp, int bus, int event) */ static void -isp_got_msg(struct ispsoftc *isp, in_entry_t *inp) +isp_got_msg(ispsoftc_t *isp, in_entry_t *inp) { tmd_notify_t nt; uint8_t status = inp->in_status & ~QLTM_SVALID; MEMZERO(&nt, sizeof (nt)); nt.nt_hba = isp; - /* nt_str set in outer layers */ nt.nt_iid = GET_IID_VAL(inp->in_iid); nt.nt_tgt = inp->in_tgt; nt.nt_lun = inp->in_lun; @@ -662,22 +662,22 @@ isp_got_msg(struct ispsoftc *isp, in_entry_t *inp) * Synthesize a message from the task management flags in a FCP_CMND_IU. */ static void -isp_got_msg_fc(struct ispsoftc *isp, in_fcentry_t *inp) +isp_got_msg_fc(ispsoftc_t *isp, in_fcentry_t *inp) { tmd_notify_t nt; static const char f1[] = "%s from iid 0x%08x%08x lun %d seq 0x%x"; static const char f2[] = "unknown %s 0x%x lun %d iid 0x%08x%08x task flags 0x%x seq 0x%x\n"; + uint16_t seqid; MEMZERO(&nt, sizeof (tmd_notify_t)); nt.nt_hba = isp; - /* - * XXX: LOOK UP TRANSLATION IN CURRENT LPORTDB - */ if (IS_2KLOGIN(isp)) { nt.nt_iid = ((in_fcentry_e_t *)inp)->in_iid; + seqid = ((in_fcentry_e_t *)inp)->in_seqid; } else { - nt.nt_iid = inp->in_iid; /* possibly reset in outer layer */ + nt.nt_iid = inp->in_iid; + seqid = inp->in_seqid; } /* nt_tgt set in outer layers */ if (FCPARAM(isp)->isp_fwattr & ISP_FW_ATTR_SCCLUN) { @@ -685,7 +685,7 @@ isp_got_msg_fc(struct ispsoftc *isp, in_fcentry_t *inp) } else { nt.nt_lun = inp->in_lun; } - IN_FC_MAKE_TAGID(nt.nt_tagval, 0, inp); + IN_FC_MAKE_TAGID(nt.nt_tagval, 0, seqid); nt.nt_lreserved = inp; if (inp->in_status != IN_MSG_RECEIVED) { @@ -727,7 +727,7 @@ isp_got_msg_fc(struct ispsoftc *isp, in_fcentry_t *inp) } void -isp_notify_ack(struct ispsoftc *isp, void *arg) +isp_notify_ack(ispsoftc_t *isp, void *arg) { char storage[QENTRY_LEN]; uint16_t nxti, optr; @@ -797,7 +797,7 @@ isp_notify_ack(struct ispsoftc *isp, void *arg) } static void -isp_handle_atio(struct ispsoftc *isp, at_entry_t *aep) +isp_handle_atio(ispsoftc_t *isp, at_entry_t *aep) { int lun; lun = aep->at_lun; @@ -878,7 +878,7 @@ isp_handle_atio(struct ispsoftc *isp, at_entry_t *aep) } static void -isp_handle_atio2(struct ispsoftc *isp, at2_entry_t *aep) +isp_handle_atio2(ispsoftc_t *isp, at2_entry_t *aep) { int lun, iid; @@ -967,7 +967,7 @@ isp_handle_atio2(struct ispsoftc *isp, at2_entry_t *aep) } static void -isp_handle_ctio(struct ispsoftc *isp, ct_entry_t *ct) +isp_handle_ctio(ispsoftc_t *isp, ct_entry_t *ct) { void *xs; int pl = ISP_LOGTDEBUG2; @@ -1127,7 +1127,7 @@ isp_handle_ctio(struct ispsoftc *isp, ct_entry_t *ct) } static void -isp_handle_ctio2(struct ispsoftc *isp, ct2_entry_t *ct) +isp_handle_ctio2(ispsoftc_t *isp, ct2_entry_t *ct) { XS_T *xs; int pl = ISP_LOGTDEBUG2; @@ -1181,7 +1181,7 @@ isp_handle_ctio2(struct ispsoftc *isp, ct2_entry_t *ct) if (fmsg == NULL) fmsg = "ABORT Task Management Function Received"; - isp_prt(isp, ISP_LOGERR, "CTIO2 destroyed by %s", fmsg); + isp_prt(isp, ISP_LOGERR, "CTIO2 destroyed by %s: RX_ID=0x%x", fmsg, ct->ct_rxid); break; case CT_INVAL: diff --git a/sys/dev/isp/isp_target.h b/sys/dev/isp/isp_target.h index 38d73c26b22a6..67637ea1d9fb5 100644 --- a/sys/dev/isp/isp_target.h +++ b/sys/dev/isp/isp_target.h @@ -388,8 +388,8 @@ typedef struct { #define FC_GET_INST AT2_GET_INST #define FC_GET_HANDLE AT2_GET_HANDLE -#define IN_FC_MAKE_TAGID(tid, inst, inp) \ - tid = inp->in_seqid; \ +#define IN_FC_MAKE_TAGID(tid, inst, seqid) \ + tid = seqid; \ tid |= (inst << 16) #define FC_TAG_INSERT_INST(tid, inst) \ @@ -667,7 +667,7 @@ void isp_notify_ack(ispsoftc_t *, void *); * (softc, cmd, bus, tgt, lun, cmd_cnt, inotify_cnt, opaque) */ #define DFLT_CMND_CNT 0xfe /* unmonitored */ -#define DFLT_INOT_CNT 16 +#define DFLT_INOT_CNT 0xfe /* unmonitored */ int isp_lun_cmd(ispsoftc_t *, int, int, int, int, int, int, uint32_t); /* diff --git a/sys/dev/isp/isp_tpublic.h b/sys/dev/isp/isp_tpublic.h index b4f6f4df60b5e..56094541ae0dc 100644 --- a/sys/dev/isp/isp_tpublic.h +++ b/sys/dev/isp/isp_tpublic.h @@ -27,38 +27,38 @@ * SUCH DAMAGE. */ /* - * Qlogic ISP Host Adapter Public Target Interface Structures && Routines + * Host Adapter Public Target Interface Structures && Routines */ -#ifndef _ISP_TPUBLIC_H -#define _ISP_TPUBLIC_H 1 +#ifndef _ISP_TPUBLIC_H +#define _ISP_TPUBLIC_H 1 /* - * Action codes set by the Qlogic MD target driver for + * Action codes set by the MD target driver for * the external layer to figure out what to do with. */ typedef enum { - QOUT_HBA_REG=0, /* the argument is a pointer to a hba_register_t */ - QOUT_ENABLE, /* the argument is a pointer to a enadis_t */ - QOUT_DISABLE, /* the argument is a pointer to a enadis_t */ - QOUT_TMD_START, /* the argument is a pointer to a tmd_cmd_t */ - QOUT_TMD_DONE, /* the argument is a pointer to a tmd_cmd_t */ - QOUT_NOTIFY, /* the argument is a pointer to a tmd_notify_t */ - QOUT_HBA_UNREG /* the argument is a pointer to a hba_register_t */ + QOUT_HBA_REG=0, /* the argument is a pointer to a hba_register_t */ + QOUT_ENABLE, /* the argument is a pointer to a enadis_t */ + QOUT_DISABLE, /* the argument is a pointer to a enadis_t */ + QOUT_TMD_START, /* the argument is a pointer to a tmd_cmd_t */ + QOUT_TMD_DONE, /* the argument is a pointer to a tmd_cmd_t */ + QOUT_NOTIFY, /* the argument is a pointer to a tmd_notify_t */ + QOUT_HBA_UNREG /* the argument is a pointer to a hba_register_t */ } tact_e; /* * Action codes set by the external layer for the - * MD Qlogic driver to figure out what to do with. + * MD driver to figure out what to do with. */ typedef enum { - QIN_HBA_REG=99, /* the argument is a pointer to a hba_register_t */ - QIN_ENABLE, /* the argument is a pointer to a enadis_t */ - QIN_DISABLE, /* the argument is a pointer to a enadis_t */ - QIN_TMD_CONT, /* the argument is a pointer to a tmd_cmd_t */ - QIN_TMD_FIN, /* the argument is a pointer to a tmd_cmd_t */ - QIN_NOTIFY_ACK, /* the argument is a pointer to a tmd_notify_t */ - QIN_HBA_UNREG, /* the argument is a pointer to a hba_register_t */ + QIN_HBA_REG=99, /* the argument is a pointer to a hba_register_t */ + QIN_ENABLE, /* the argument is a pointer to a enadis_t */ + QIN_DISABLE, /* the argument is a pointer to a enadis_t */ + QIN_TMD_CONT, /* the argument is a pointer to a tmd_cmd_t */ + QIN_TMD_FIN, /* the argument is a pointer to a tmd_cmd_t */ + QIN_NOTIFY_ACK, /* the argument is a pointer to a tmd_notify_t */ + QIN_HBA_UNREG, /* the argument is a pointer to a hba_register_t */ } qact_e; /* @@ -71,14 +71,14 @@ typedef enum { * in, and the external module to call back with a QIN_HBA_REG that * passes back the corresponding information. */ -#define QR_VERSION 2 +#define QR_VERSION 10 typedef struct { - void * r_identity; - void (*r_action)(qact_e, void *); - char r_name[8]; - int r_inst; - int r_version; - enum { R_FC, R_SCSI } r_type; + void * r_identity; + void (*r_action)(qact_e, void *); + char r_name[8]; + int r_inst; + int r_version; + enum { R_FC, R_SCSI } r_type; } hba_register_t; /* @@ -123,21 +123,19 @@ typedef struct tmd_notify { /* * A word about ENABLE/DISABLE: the argument is a pointer to a enadis_t - * with cd_hba, cd_iid, cd_chan, cd_tgt and cd_lun filled out. + * with en_hba, en_iid, en_chan, en_tgt and en_lun filled out. * * If an error occurs in either enabling or disabling the described lun * cd_error is set with an appropriate non-zero value. - * - * Logical unit zero must be the first enabled and the last disabled. */ typedef struct { - void * en_private; /* for outer layer usage */ - void * en_hba; /* HBA tag */ - uint64_t en_iid; /* initiator ID */ - uint64_t en_tgt; /* target id */ - uint64_t en_lun; /* logical unit */ - uint8_t en_chan; /* channel on card */ - int32_t en_error; + void * en_private; /* for outer layer usage */ + void * en_hba; /* HBA tag */ + uint64_t en_iid; /* initiator ID */ + uint64_t en_tgt; /* target id */ + uint16_t en_lun; /* logical unit */ + uint16_t en_chan; /* channel on card */ + int en_error; } enadis_t; /* @@ -173,29 +171,23 @@ typedef struct { * mode command is coming from. The outer layer has to pass this back * unchanged to avoid chaos. * - * The cd_iid, cd_tgt, cd_lun and cd_bus tags are used to identify the + * The cd_iid, cd_tgt, cd_lun and cd_port tags are used to identify the * id of the initiator who sent us a command, the target claim to be, the - * lun on the target we claim to be, and the bus instance (for multiple - * bus host adapters) that this applies to (consider it an extra Port + * lun on the target we claim to be, and the port instance (for multiple + * port host adapters) that this applies to (consider it an extra port * parameter). The iid, tgt and lun values are deliberately chosen to be * fat so that, for example, World Wide Names can be used instead of - * the units that the Qlogic firmware uses (in the case where the MD + * the units that the firmware uses (in the case where the MD * layer maintains a port database, for example). * - * The cd_tagtype field specifies what kind of command tag has been - * sent with the command. The cd_tagval is the tag's value (low 16 - * bits). It also contains (in the upper 16 bits) any command handle. - * - * - * N.B.: when the MD layer sends this command to outside software - * the outside software likely *MUST* return the same cd_tagval that - * was in place because this value is likely what the Qlogic f/w uses - * to identify a command. + * The cd_tagtype field specifies what kind of command tag type, if + * any, has been sent with the command. Note that the Outer Layer + * still needs to pass the tag handle through unchanged even + * if the tag type is CD_UNTAGGED. * * The cd_cdb contains storage for the passed in command descriptor block. - * This is the maximum size we can get out of the Qlogic f/w. There's no - * passed in length because whoever decodes the command to act upon it - * will know what the appropriate length is. + * There is no need to define length as the callee should be able to + * figure this out. * * The tag cd_lflags are the flags set by the MD driver when it gets * command incoming or when it needs to inform any outside entities @@ -219,10 +211,11 @@ typedef struct { * The tag cd_data points to a data segment to either be filled or * read from depending on the direction of data movement. The tag * is undefined if no data direction is set. The MD layer and outer - * layers must agree on the meaning of cd_data. + * layers must agree on the meaning of cd_data and it is specifically + * not defined here. * * The tag cd_totlen is the total data amount expected to be moved - * over the life of the command. It *may* be set by the MD layer, possibly + * over the life of the command. It may be set by the MD layer, possibly * from the datalen field of an FCP CMND IU unit. If it shows up in the outer * layers set to zero and the CDB indicates data should be moved, the outer * layer should set it to the amount expected to be moved. @@ -231,28 +224,14 @@ typedef struct { * The outer layers need to set this at the begining of command processing * to equal cd_totlen. As data is successfully moved, this value is decreased. * At the end of a command, any nonzero residual indicates the number of bytes - * requested but not moved. XXXXXXXXXXXXXXXXXXXXXXX TOO VAGUE!!! + * requested by the command but not moved. * * The tag cd_xfrlen is the length of the currently active data transfer. * This allows several interations between any outside software and the * MD layer to move data. * * The reason that total length and total residual have to be tracked - * is that fibre channel FCP DATA IU units have to have a relative - * offset field. - * - * N.B.: there is no necessary 1-to-1 correspondence between any one - * data transfer segment and the number of CTIOs that will be generated - * satisfy the current data transfer segment. It's not also possible to - * predict how big a transfer can be before it will be 'too big'. Be - * reasonable- a 64KB transfer is 'reasonable'. A 1MB transfer may not - * be. A 32MB transfer is unreasonable. The problem here has to do with - * how CTIOs can be used to map passed data pointers. In systems which - * have page based scatter-gather requirements, each PAGESIZEd chunk will - * consume one data segment descriptor- you get 3 or 4 of them per CTIO. - * The size of the REQUEST QUEUE you drop a CTIO onto is finite (typically - * it's 256, but on some systems it's even smaller, and note you have to - * sure this queue with the initiator side of this driver). + * is to keep track of relative offset. * * The tags cd_sense and cd_scsi_status are pretty obvious. * @@ -264,51 +243,53 @@ typedef struct { * */ -#ifndef TMD_CDBLEN -#define TMD_CDBLEN 16 +#ifndef TMD_CDBLEN +#define TMD_CDBLEN 16 #endif -#ifndef TMD_SENSELEN -#define TMD_SENSELEN 24 +#ifndef TMD_SENSELEN +#define TMD_SENSELEN 18 #endif -#ifndef QCDS -#define QCDS 8 +#ifndef QCDS +#define QCDS 8 #endif typedef struct tmd_cmd { - void * cd_private; /* private data pointer */ - void * cd_hba; /* HBA tag */ - void * cd_data; /* 'pointer' to data */ - uint64_t cd_iid; /* initiator ID */ - uint64_t cd_tgt; /* target id */ - uint64_t cd_lun; /* logical unit */ - uint32_t cd_tagval; /* tag value */ - uint32_t cd_lflags; /* flags lower level sets */ - uint32_t cd_hflags; /* flags higher level sets */ - uint32_t cd_totlen; /* total data requirement */ - uint32_t cd_resid; /* total data residual */ - uint32_t cd_xfrlen; /* current data requirement */ - int32_t cd_error; /* current error */ - uint32_t - cd_scsi_status : 16, /* closing SCSI status */ - : 7, - cd_chan : 1, /* channel on card */ - : 2, - cd_tagtype : 6; /* tag type */ - uint8_t cd_senselen; - uint8_t cd_cdblen; - uint8_t cd_sense[TMD_SENSELEN]; - uint8_t cd_cdb[TMD_CDBLEN]; /* Command */ - union { - void * ptrs[QCDS / sizeof (void *)]; - uint64_t llongs[QCDS / sizeof (uint64_t)]; - uint32_t longs[QCDS / sizeof (uint32_t)]; - uint16_t shorts[QCDS / sizeof (uint16_t)]; - uint8_t bytes[QCDS]; - } cd_lreserved[2], cd_hreserved[2]; + void * cd_private; /* private data pointer */ + void * cd_hba; /* HBA tag */ + void * cd_data; /* 'pointer' to data */ + uint64_t cd_iid; /* initiator ID */ + uint64_t cd_tgt; /* target id */ + uint64_t cd_lun; /* logical unit */ + uint32_t cd_tagval; /* tag value */ + uint32_t cd_lflags; /* flags lower level sets */ + uint32_t cd_hflags; /* flags higher level sets */ + uint32_t cd_totlen; /* total data load */ + uint32_t cd_resid; /* total data residual */ + uint32_t cd_xfrlen; /* current data load */ + int32_t cd_error; /* current error */ + uint8_t cd_tagtype : 4, + cd_port : 4; /* port number on HBA */ + uint8_t cd_scsi_status; + uint8_t cd_sense[TMD_SENSELEN]; + uint8_t cd_cdb[TMD_CDBLEN]; + union { + void * ptrs[QCDS / sizeof (void *)]; + uint64_t llongs[QCDS / sizeof (uint64_t)]; + uint32_t longs[QCDS / sizeof (uint32_t)]; + uint16_t shorts[QCDS / sizeof (uint16_t)]; + uint8_t bytes[QCDS]; + } cd_lreserved[2], cd_hreserved[2]; } tmd_cmd_t; -#ifndef TMD_SIZE -#define TMD_SIZE (sizeof (tmd_cmd_t)) +/* defined tags */ +#define CD_UNTAGGED 0 +#define CD_SIMPLE_TAG 1 +#define CD_ORDERED_TAG 2 +#define CD_HEAD_TAG 3 +#define CD_ACA_TAG 4 + +#ifndef TMD_SIZE +#define TMD_SIZE (sizeof (tmd_cmd_t)) #endif /* @@ -324,49 +305,50 @@ typedef struct tmd_cmd { * be transferred in any QOUT_TMD_CONT call is cd_xfrlen- the * flags CDFH_DATA_IN and CDFH_DATA_OUT define which direction. */ -#define CDFL_SNSVALID 0x01 /* sense data (from f/w) good */ -#define CDFL_SENTSTATUS 0x02 /* last action sent status */ -#define CDFL_DATA_IN 0x04 /* target (us) -> initiator (them) */ -#define CDFL_DATA_OUT 0x08 /* initiator (them) -> target (us) */ -#define CDFL_BIDIR 0x0C /* bidirectional data */ -#define CDFL_ERROR 0x10 /* last action ended in error */ -#define CDFL_NODISC 0x20 /* disconnects disabled */ -#define CDFL_SENTSENSE 0x40 /* last action sent sense data */ -#define CDFL_BUSY 0x80 /* this command is not on a free list */ -#define CDFL_PRIVATE 0xFF000000 /* private layer flags */ +#define CDFL_SNSVALID 0x01 /* sense data (from f/w) good */ +#define CDFL_SENTSTATUS 0x02 /* last action sent status */ +#define CDFL_DATA_IN 0x04 /* target (us) -> initiator (them) */ +#define CDFL_DATA_OUT 0x08 /* initiator (them) -> target (us) */ +#define CDFL_BIDIR 0x0C /* bidirectional data */ +#define CDFL_ERROR 0x10 /* last action ended in error */ +#define CDFL_NODISC 0x20 /* disconnects disabled */ +#define CDFL_SENTSENSE 0x40 /* last action sent sense data */ +#define CDFL_BUSY 0x80 /* this command is not on a free list */ +#define CDFL_PRIVATE 0xFF000000 /* private layer flags */ -#define CDFH_SNSVALID 0x01 /* sense data (from outer layer) good */ -#define CDFH_STSVALID 0x02 /* status valid */ -#define CDFH_DATA_IN 0x04 /* target (us) -> initiator (them) */ -#define CDFH_DATA_OUT 0x08 /* initiator (them) -> target (us) */ -#define CDFH_DATA_MASK 0x0C /* mask to cover data direction */ -#define CDFH_PRIVATE 0xFF000000 /* private layer flags */ +#define CDFH_SNSVALID 0x01 /* sense data (from outer layer) good */ +#define CDFH_STSVALID 0x02 /* status valid */ +#define CDFH_DATA_IN 0x04 /* target (us) -> initiator (them) */ +#define CDFH_DATA_OUT 0x08 /* initiator (them) -> target (us) */ +#define CDFH_DATA_MASK 0x0C /* mask to cover data direction */ +#define CDFH_PRIVATE 0xFF000000 /* private layer flags */ /* * A word about the START/CONT/DONE/FIN dance: * - * When the HBA is enabled for receiving commands, one may show up - * without notice. When that happens, the Qlogic target mode driver - * gets a tmd_cmd_t, fills it with the info that just arrived, and - * calls the outer layer with a QOUT_TMD_START code and pointer to - * the tmd_cmd_t. + * When the HBA is enabled for receiving commands, one may show up + * without notice. When that happens, the MD target mode driver + * gets a tmd_cmd_t, fills it with the info that just arrived, and + * calls the outer layer with a QOUT_TMD_START code and pointer to + * the tmd_cmd_t. * - * The outer layer decodes the command, fetches data, prepares stuff, - * whatever, and starts by passing back the pointer with a QIN_TMD_CONT - * code which causes the Qlogic target mode driver to generate CTIOs to - * satisfy whatever action needs to be taken. When those CTIOs complete, - * the Qlogic target driver sends the pointer to the cmd_tmd_t back with - * a QOUT_TMD_DONE code. This repeats for as long as necessary. + * The outer layer decodes the command, fetches data, prepares stuff, + * whatever, and starts by passing back the pointer with a QIN_TMD_CONT + * code which causes the MD target mode driver to generate CTIOs to + * satisfy whatever action needs to be taken. When those CTIOs complete, + * the MD target driver sends the pointer to the cmd_tmd_t back with + * a QOUT_TMD_DONE code. This repeats for as long as necessary. These + * may not be done in parallel- they are sequential operations. * - * The outer layer signals it wants to end the command by settings within - * the tmd_cmd_t itself. When the final QIN_TMD_CONT is reported completed, - * the outer layer frees the tmd_cmd_t by sending the pointer to it - * back with a QIN_TMD_FIN code. + * The outer layer signals it wants to end the command by settings within + * the tmd_cmd_t itself. When the final QIN_TMD_CONT is reported completed, + * the outer layer frees the tmd_cmd_t by sending the pointer to it + * back with a QIN_TMD_FIN code. * - * The graph looks like: + * The graph looks like: * - * QOUT_TMD_START -> [ QIN_TMD_CONT -> QOUT_TMD_DONE ] * -> QIN_TMD_FIN. + * QOUT_TMD_START -> [ QIN_TMD_CONT -> QOUT_TMD_DONE ] * -> QIN_TMD_FIN. * */ @@ -376,11 +358,14 @@ typedef struct tmd_cmd { * The MD target handler function (the outer layer calls this) * should be be prototyped like: * - * void target_action(qact_e, void *arg) + * void target_action(qact_e, void *arg) * * The outer layer target handler function (the MD layer calls this) * should be be prototyped like: * - * void system_target_handler(tact_e, void *arg) + * void scsi_target_handler(tact_e, void *arg) + */ +#endif /* _ISP_TPUBLIC_H */ +/* + * vim:ts=4:sw=4:expandtab */ -#endif /* _ISP_TPUBLIC_H */ diff --git a/sys/dev/isp/ispmbox.h b/sys/dev/isp/ispmbox.h index 490495eec68c0..e79efa232ca7d 100644 --- a/sys/dev/isp/ispmbox.h +++ b/sys/dev/isp/ispmbox.h @@ -708,6 +708,10 @@ typedef struct isp_icb { #define ICB_DFLT_RDELAY 5 #define ICB_DFLT_RCOUNT 3 +#define ICB_LOGIN_TOV 30 +#define ICB_LUN_ENABLE_TOV 180 + + #define RQRSP_ADDR0015 0 #define RQRSP_ADDR1631 1 |
