isp_freebsd.h revision 146734
11592Srgrimes/* $FreeBSD: head/sys/dev/isp/isp_freebsd.h 146734 2005-05-29 04:42:30Z nyan $ */
21592Srgrimes/*-
31592Srgrimes * Qlogic ISP SCSI Host Adapter FreeBSD Wrapper Definitions
41592Srgrimes * Copyright (c) 1997, 1998, 1999, 2000, 2001, 2002 by Matthew Jacob
51592Srgrimes *
61592Srgrimes * Redistribution and use in source and binary forms, with or without
71592Srgrimes * modification, are permitted provided that the following conditions
81592Srgrimes * are met:
91592Srgrimes * 1. Redistributions of source code must retain the above copyright
101592Srgrimes *    notice immediately at the beginning of the file, without modification,
111592Srgrimes *    this list of conditions, and the following disclaimer.
121592Srgrimes * 2. The name of the author may not be used to endorse or promote products
131592Srgrimes *    derived from this software without specific prior written permission.
141592Srgrimes *
151592Srgrimes * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
161592Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
171592Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
181592Srgrimes * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
191592Srgrimes * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
201592Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21262136Sbrueffer * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
221592Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
231592Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
241592Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
251592Srgrimes * SUCH DAMAGE.
261592Srgrimes */
271592Srgrimes#ifndef	_ISP_FREEBSD_H
281592Srgrimes#define	_ISP_FREEBSD_H
291592Srgrimes
301592Srgrimes#define	ISP_PLATFORM_VERSION_MAJOR	5
311592Srgrimes#define	ISP_PLATFORM_VERSION_MINOR	9
321592Srgrimes
331592Srgrimes#include <sys/param.h>
341592Srgrimes#include <sys/systm.h>
351592Srgrimes#include <sys/endian.h>
361592Srgrimes#include <sys/kernel.h>
3727074Ssteve#include <sys/queue.h>
381592Srgrimes#include <sys/lock.h>
3927074Ssteve#include <sys/malloc.h>
401592Srgrimes#include <sys/mutex.h>
411592Srgrimes#include <sys/condvar.h>
421592Srgrimes#include <sys/proc.h>
431592Srgrimes#include <sys/bus.h>
4431386Scharnier
4527077Ssteve#include <machine/bus.h>
4631386Scharnier#include <machine/clock.h>
4731386Scharnier#include <machine/cpu.h>
4850476Speter
491592Srgrimes#include <cam/cam.h>
501592Srgrimes#include <cam/cam_debug.h>
511592Srgrimes#include <cam/cam_ccb.h>
521592Srgrimes#include <cam/cam_sim.h>
53129652Sstefanf#include <cam/cam_xpt.h>
541592Srgrimes#include <cam/cam_xpt_sim.h>
551592Srgrimes#include <cam/cam_debug.h>
561592Srgrimes#include <cam/scsi/scsi_all.h>
571592Srgrimes#include <cam/scsi/scsi_message.h>
581592Srgrimes
591592Srgrimes#include "opt_ddb.h"
601592Srgrimes#include "opt_isp.h"
611592Srgrimes
621592Srgrimes#ifdef	PAE
631592Srgrimes#define	ISP_DAC_SUPPORTED	1
641592Srgrimes#endif
651592Srgrimes
661592Srgrimes/*
671592Srgrimes * Efficiency- get rid of SBus code && tests unless we need them.
681592Srgrimes */
691592Srgrimes#if	_MACHINE_ARCH == sparc64
701592Srgrimes#define	ISP_SBUS_SUPPORTED	1
711592Srgrimes#else
721592Srgrimes#define	ISP_SBUS_SUPPORTED	0
731592Srgrimes#endif
741592Srgrimes
751592Srgrimes#define	HANDLE_LOOPSTATE_IN_OUTER_LAYERS	1
761592Srgrimes/* #define	ISP_SMPLOCK			1 */
771592Srgrimes
781592Srgrimes#ifdef	ISP_SMPLOCK
791592Srgrimes#define	ISP_IFLAGS	INTR_TYPE_CAM | INTR_ENTROPY | INTR_MPSAFE
801592Srgrimes#else
811592Srgrimes#define	ISP_IFLAGS	INTR_TYPE_CAM | INTR_ENTROPY
821592Srgrimes#endif
831592Srgrimes
841592Srgrimestypedef void ispfwfunc(int, int, int, u_int16_t **);
851592Srgrimes
8690377Simp#ifdef	ISP_TARGET_MODE
871592Srgrimes#define	ISP_TARGET_FUNCTIONS	1
881592Srgrimes#define	ATPDPSIZE	256
891592Srgrimestypedef struct {
901592Srgrimes	u_int32_t	orig_datalen;
911592Srgrimes	u_int32_t	bytes_xfered;
921592Srgrimes	u_int32_t	last_xframt;
931592Srgrimes	u_int32_t	tag	: 16,
941592Srgrimes			lun	: 13,	/* not enough */
951592Srgrimes			state	: 3;
961592Srgrimes} atio_private_data_t;
971592Srgrimes#define	ATPD_STATE_FREE			0
981592Srgrimes#define	ATPD_STATE_ATIO			1
991592Srgrimes#define	ATPD_STATE_CAM			2
1001592Srgrimes#define	ATPD_STATE_CTIO			3
1011592Srgrimes#define	ATPD_STATE_LAST_CTIO		4
1021592Srgrimes#define	ATPD_STATE_PDON			5
1031592Srgrimes
1041592Srgrimestypedef struct tstate {
1051592Srgrimes	struct tstate *next;
1061592Srgrimes	struct cam_path *owner;
1071592Srgrimes	struct ccb_hdr_slist atios;
1081592Srgrimes	struct ccb_hdr_slist inots;
1091592Srgrimes	lun_id_t lun;
1101592Srgrimes	int bus;
1111592Srgrimes	u_int32_t hold;
1121592Srgrimes	int atio_count;
11327074Ssteve	int inot_count;
1141592Srgrimes} tstate_t;
1151592Srgrimes
1161592Srgrimes#define	LUN_HASH_SIZE			32
1171592Srgrimes#define	LUN_HASH_FUNC(isp, port, lun)					\
1181592Srgrimes	((IS_DUALBUS(isp)) ?						\
1191592Srgrimes		(((lun) & ((LUN_HASH_SIZE >> 1) - 1)) << (port)) :	\
1201592Srgrimes		((lun) & (LUN_HASH_SIZE - 1)))
1211592Srgrimes#endif
1221592Srgrimes
1231592Srgrimesstruct isposinfo {
1241592Srgrimes	struct ispsoftc *	next;
1251592Srgrimes	u_int64_t		default_port_wwn;
1261592Srgrimes	u_int64_t		default_node_wwn;
1271592Srgrimes	u_int32_t		default_id;
1281592Srgrimes	device_t		dev;
1291592Srgrimes	struct cam_sim		*sim;
1301592Srgrimes	struct cam_path		*path;
1311592Srgrimes	struct cam_sim		*sim2;
1321592Srgrimes	struct cam_path		*path2;
1331592Srgrimes	struct intr_config_hook	ehook;
1341592Srgrimes	u_int8_t		: 1,
1351592Srgrimes		fcbsy		: 1,
1361592Srgrimes		ktmature	: 1,
1371592Srgrimes		mboxwaiting	: 1,
1381592Srgrimes		intsok		: 1,
1391592Srgrimes		simqfrozen	: 3;
1401592Srgrimes	struct mtx		lock;
1411592Srgrimes	struct cv		kthread_cv;
1421592Srgrimes	struct proc		*kproc;
1431592Srgrimes	bus_dma_tag_t		cdmat;
1441592Srgrimes	bus_dmamap_t		cdmap;
1451592Srgrimes#define	isp_cdmat		isp_osinfo.cdmat
1461592Srgrimes#define	isp_cdmap		isp_osinfo.cdmap
1471592Srgrimes#ifdef	ISP_TARGET_MODE
1481592Srgrimes#define	TM_WILDCARD_ENABLED	0x02
1491592Srgrimes#define	TM_TMODE_ENABLED	0x01
1501592Srgrimes	u_int8_t		tmflags[2];	/* two busses */
1511592Srgrimes#define	NLEACT	4
1521592Srgrimes	union ccb *		leact[NLEACT];
1531592Srgrimes	tstate_t		tsdflt[2];	/* two busses */
1541592Srgrimes	tstate_t		*lun_hash[LUN_HASH_SIZE];
1551592Srgrimes	atio_private_data_t	atpdp[ATPDPSIZE];
1561592Srgrimes#endif
1571592Srgrimes};
1581592Srgrimes
1591592Srgrimes#define	isp_lock	isp_osinfo.lock
1601592Srgrimes
1611592Srgrimes/*
1621592Srgrimes * Locking macros...
1631592Srgrimes */
1641592Srgrimes
1651592Srgrimes#ifdef	ISP_SMPLOCK
1661592Srgrimes#define	ISP_LOCK(x)		mtx_lock(&(x)->isp_lock)
1671592Srgrimes#define	ISP_UNLOCK(x)		mtx_unlock(&(x)->isp_lock)
1681592Srgrimes#define	ISPLOCK_2_CAMLOCK(isp)	\
1691592Srgrimes	mtx_unlock(&(isp)->isp_lock); mtx_lock(&Giant)
1701592Srgrimes#define	CAMLOCK_2_ISPLOCK(isp)	\
1711592Srgrimes	mtx_unlock(&Giant); mtx_lock(&(isp)->isp_lock)
1721592Srgrimes#else
1731592Srgrimes#define	ISP_LOCK(x)		do { } while (0)
17490377Simp#define	ISP_UNLOCK(x)		do { } while (0)
1751592Srgrimes#define	ISPLOCK_2_CAMLOCK(isp)	do { } while (0)
17627079Ssteve#define	CAMLOCK_2_ISPLOCK(isp)	do { } while (0)
17727079Ssteve#endif
17827079Ssteve
1791592Srgrimes/*
1801592Srgrimes * Required Macros/Defines
1811592Srgrimes */
1821592Srgrimes
1831592Srgrimes#define	INLINE			__inline
1841592Srgrimes
1851592Srgrimes#define	ISP2100_SCRLEN		0x800
1861592Srgrimes
1871592Srgrimes#define	MEMZERO			bzero
1881592Srgrimes#define	MEMCPY(dst, src, amt)	bcopy((src), (dst), (amt))
18927074Ssteve#define	SNPRINTF		snprintf
1901592Srgrimes#define	USEC_DELAY		DELAY
1911592Srgrimes#define	USEC_SLEEP(isp, x)		\
1921592Srgrimes	if (isp->isp_osinfo.intsok)	\
1931592Srgrimes		ISP_UNLOCK(isp);	\
1941592Srgrimes	DELAY(x);			\
1951592Srgrimes	if (isp->isp_osinfo.intsok)	\
1961592Srgrimes		ISP_LOCK(isp)
1971592Srgrimes
1981592Srgrimes#define	NANOTIME_T		struct timespec
1991592Srgrimes#define	GET_NANOTIME		nanotime
2001592Srgrimes#define	GET_NANOSEC(x)		((x)->tv_sec * 1000000000 + (x)->tv_nsec)
2011592Srgrimes#define	NANOTIME_SUB		nanotime_sub
2021592Srgrimes
2031592Srgrimes#define	MAXISPREQUEST(isp)	((IS_FC(isp) || IS_ULTRA2(isp))? 1024 : 256)
2041592Srgrimes
2051592Srgrimes#define	MEMORYBARRIER(isp, type, offset, size)			\
2061592Srgrimesswitch (type) {							\
2071592Srgrimescase SYNC_SFORDEV:						\
2081592Srgrimescase SYNC_REQUEST:						\
2091592Srgrimes	bus_dmamap_sync(isp->isp_cdmat, isp->isp_cdmap, 	\
2101592Srgrimes	   BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);		\
2111592Srgrimes	break;							\
2121592Srgrimescase SYNC_SFORCPU:						\
2131592Srgrimescase SYNC_RESULT:						\
2141592Srgrimes	bus_dmamap_sync(isp->isp_cdmat, isp->isp_cdmap,		\
2151592Srgrimes	   BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);	\
2161592Srgrimes	break;							\
2171592Srgrimesdefault:							\
2181592Srgrimes	break;							\
2191592Srgrimes}
2201592Srgrimes
2211592Srgrimes#define	MBOX_ACQUIRE(isp)
2221592Srgrimes#define	MBOX_WAIT_COMPLETE		isp_mbox_wait_complete
2231592Srgrimes#define	MBOX_NOTIFY_COMPLETE(isp)	\
2241592Srgrimes	if (isp->isp_osinfo.mboxwaiting) { \
22590377Simp		isp->isp_osinfo.mboxwaiting = 0; \
2261592Srgrimes		wakeup(&isp->isp_mbxworkp); \
22727079Ssteve	} \
22827079Ssteve	isp->isp_mboxbsy = 0
22927079Ssteve#define	MBOX_RELEASE(isp)
23027079Ssteve
2311592Srgrimes#define	FC_SCRATCH_ACQUIRE(isp)						\
2321592Srgrimes	if (isp->isp_osinfo.fcbsy) {					\
2331592Srgrimes		isp_prt(isp, ISP_LOGWARN,				\
2341592Srgrimes		    "FC scratch area busy (line %d)!", __LINE__);	\
2351592Srgrimes	} else								\
2361592Srgrimes		isp->isp_osinfo.fcbsy = 1
2371592Srgrimes#define	FC_SCRATCH_RELEASE(isp)		 isp->isp_osinfo.fcbsy = 0
2381592Srgrimes
2391592Srgrimes#ifndef	SCSI_GOOD
2401592Srgrimes#define	SCSI_GOOD	SCSI_STATUS_OK
2411592Srgrimes#endif
24227074Ssteve#ifndef	SCSI_CHECK
2431592Srgrimes#define	SCSI_CHECK	SCSI_STATUS_CHECK_COND
2441592Srgrimes#endif
2451592Srgrimes#ifndef	SCSI_BUSY
2461592Srgrimes#define	SCSI_BUSY	SCSI_STATUS_BUSY
2471592Srgrimes#endif
2481592Srgrimes#ifndef	SCSI_QFULL
2491592Srgrimes#define	SCSI_QFULL	SCSI_STATUS_QUEUE_FULL
2501592Srgrimes#endif
2511592Srgrimes
2521592Srgrimes#define	XS_T			struct ccb_scsiio
2531592Srgrimes#define	XS_ISP(ccb)		((struct ispsoftc *) (ccb)->ccb_h.spriv_ptr1)
2541592Srgrimes#define	XS_CHANNEL(ccb)		cam_sim_bus(xpt_path_sim((ccb)->ccb_h.path))
2551592Srgrimes#define	XS_TGT(ccb)		(ccb)->ccb_h.target_id
2561592Srgrimes#define	XS_LUN(ccb)		(ccb)->ccb_h.target_lun
2571592Srgrimes
2581592Srgrimes#define	XS_CDBP(ccb)	\
2591592Srgrimes	(((ccb)->ccb_h.flags & CAM_CDB_POINTER)? \
2601592Srgrimes	 (ccb)->cdb_io.cdb_ptr : (ccb)->cdb_io.cdb_bytes)
2611592Srgrimes
2621592Srgrimes#define	XS_CDBLEN(ccb)		(ccb)->cdb_len
2631592Srgrimes#define	XS_XFRLEN(ccb)		(ccb)->dxfer_len
2641592Srgrimes#define	XS_TIME(ccb)		(ccb)->ccb_h.timeout
2651592Srgrimes#define	XS_RESID(ccb)		(ccb)->resid
2661592Srgrimes#define	XS_STSP(ccb)		(&(ccb)->scsi_status)
2671592Srgrimes#define	XS_SNSP(ccb)		(&(ccb)->sense_data)
2681592Srgrimes
2691592Srgrimes#define	XS_SNSLEN(ccb)		\
2701592Srgrimes	imin((sizeof((ccb)->sense_data)), ccb->sense_len)
2711592Srgrimes
2721592Srgrimes#define	XS_SNSKEY(ccb)		((ccb)->sense_data.flags & 0xf)
2731592Srgrimes#define	XS_TAG_P(ccb)	\
2741592Srgrimes	(((ccb)->ccb_h.flags & CAM_TAG_ACTION_VALID) && \
2751592Srgrimes	 (ccb)->tag_action != CAM_TAG_ACTION_NONE)
2761592Srgrimes
2771592Srgrimes#define	XS_TAG_TYPE(ccb)	\
2781592Srgrimes	((ccb->tag_action == MSG_SIMPLE_Q_TAG)? REQFLAG_STAG : \
2791592Srgrimes	 ((ccb->tag_action == MSG_HEAD_OF_Q_TAG)? REQFLAG_HTAG : REQFLAG_OTAG))
2801592Srgrimes
2811592Srgrimes
2821592Srgrimes#define	XS_SETERR(ccb, v)	(ccb)->ccb_h.status &= ~CAM_STATUS_MASK, \
2831592Srgrimes				(ccb)->ccb_h.status |= v, \
2841592Srgrimes				(ccb)->ccb_h.spriv_field0 |= ISP_SPRIV_ERRSET
28590377Simp
2861592Srgrimes#	define	HBA_NOERROR		CAM_REQ_INPROG
2871592Srgrimes#	define	HBA_BOTCH		CAM_UNREC_HBA_ERROR
2881592Srgrimes#	define	HBA_CMDTIMEOUT		CAM_CMD_TIMEOUT
2891592Srgrimes#	define	HBA_SELTIMEOUT		CAM_SEL_TIMEOUT
29027079Ssteve#	define	HBA_TGTBSY		CAM_SCSI_STATUS_ERROR
29127079Ssteve#	define	HBA_BUSRESET		CAM_SCSI_BUS_RESET
29227079Ssteve#	define	HBA_ABORTED		CAM_REQ_ABORTED
2931592Srgrimes#	define	HBA_DATAOVR		CAM_DATA_RUN_ERR
2941592Srgrimes#	define	HBA_ARQFAIL		CAM_AUTOSENSE_FAIL
2951592Srgrimes
2961592Srgrimes
2971592Srgrimes#define	XS_ERR(ccb)		((ccb)->ccb_h.status & CAM_STATUS_MASK)
2981592Srgrimes
2991592Srgrimes#define	XS_NOERR(ccb)		\
3001592Srgrimes	(((ccb)->ccb_h.spriv_field0 & ISP_SPRIV_ERRSET) == 0 || \
3011592Srgrimes	 ((ccb)->ccb_h.status & CAM_STATUS_MASK) == CAM_REQ_INPROG)
3021592Srgrimes
3031592Srgrimes#define	XS_INITERR(ccb)		\
3041592Srgrimes	XS_SETERR(ccb, CAM_REQ_INPROG), (ccb)->ccb_h.spriv_field0 = 0
3051592Srgrimes
3061592Srgrimes#define	XS_SAVE_SENSE(xs, sp)				\
3071592Srgrimes	(xs)->ccb_h.status |= CAM_AUTOSNS_VALID,	\
3081592Srgrimes	bcopy(sp->req_sense_data, &(xs)->sense_data,	\
3091592Srgrimes	    imin(XS_SNSLEN(xs), sp->req_sense_len))
3101592Srgrimes
31127074Ssteve#define	XS_SET_STATE_STAT(a, b, c)
31227074Ssteve
3131592Srgrimes#define	DEFAULT_IID(x)		(isp)->isp_osinfo.default_id
3141592Srgrimes#define	DEFAULT_LOOPID(x)	(isp)->isp_osinfo.default_id
3151592Srgrimes#define	DEFAULT_NODEWWN(isp)	(isp)->isp_osinfo.default_node_wwn
3161592Srgrimes#define	DEFAULT_PORTWWN(isp)	(isp)->isp_osinfo.default_port_wwn
3171592Srgrimes#define	ISP_NODEWWN(isp)	FCPARAM(isp)->isp_nodewwn
3181592Srgrimes#define	ISP_PORTWWN(isp)	FCPARAM(isp)->isp_portwwn
3191592Srgrimes
3201592Srgrimes#if	BYTE_ORDER == BIG_ENDIAN
3211592Srgrimes#ifdef	ISP_SBUS_SUPPORTED
3221592Srgrimes#define	ISP_IOXPUT_8(isp, s, d)		*(d) = s
3231592Srgrimes#define	ISP_IOXPUT_16(isp, s, d)				\
3241592Srgrimes	*(d) = (isp->isp_bustype == ISP_BT_SBUS)? s : bswap16(s)
3251592Srgrimes#define	ISP_IOXPUT_32(isp, s, d)				\
3261592Srgrimes	*(d) = (isp->isp_bustype == ISP_BT_SBUS)? s : bswap32(s)
3271592Srgrimes#define	ISP_IOXGET_8(isp, s, d)		d = (*((u_int8_t *)s))
3281592Srgrimes#define	ISP_IOXGET_16(isp, s, d)				\
3291592Srgrimes	d = (isp->isp_bustype == ISP_BT_SBUS)?			\
3301592Srgrimes	*((u_int16_t *)s) : bswap16(*((u_int16_t *)s))
3311592Srgrimes#define	ISP_IOXGET_32(isp, s, d)				\
3321592Srgrimes	d = (isp->isp_bustype == ISP_BT_SBUS)?			\
33327079Ssteve	*((u_int32_t *)s) : bswap32(*((u_int32_t *)s))
3341592Srgrimes#else
3351592Srgrimes#define	ISP_IOXPUT_8(isp, s, d)		*(d) = s
3361592Srgrimes#define	ISP_IOXPUT_16(isp, s, d)	*(d) = bswap16(s)
3371592Srgrimes#define	ISP_IOXPUT_32(isp, s, d)	*(d) = bswap32(s)
3381592Srgrimes#define	ISP_IOXGET_8(isp, s, d)		d = (*((u_int8_t *)s))
3391592Srgrimes#define	ISP_IOXGET_16(isp, s, d)	d = bswap16(*((u_int16_t *)s))
3401592Srgrimes#define	ISP_IOXGET_32(isp, s, d)	d = bswap32(*((u_int32_t *)s))
3411592Srgrimes#endif
3421592Srgrimes#define	ISP_SWIZZLE_NVRAM_WORD(isp, rp)	*rp = bswap16(*rp)
3431592Srgrimes#else
3441592Srgrimes#define	ISP_IOXPUT_8(isp, s, d)		*(d) = s
3451592Srgrimes#define	ISP_IOXPUT_16(isp, s, d)	*(d) = s
3461592Srgrimes#define	ISP_IOXPUT_32(isp, s, d)	*(d) = s
3471592Srgrimes#define	ISP_IOXGET_8(isp, s, d)		d = *(s)
3481592Srgrimes#define	ISP_IOXGET_16(isp, s, d)	d = *(s)
3491592Srgrimes#define	ISP_IOXGET_32(isp, s, d)	d = *(s)
3501592Srgrimes#define	ISP_SWIZZLE_NVRAM_WORD(isp, rp)
3511592Srgrimes#endif
3521592Srgrimes
3531592Srgrimes/*
3541592Srgrimes * Includes of common header files
3551592Srgrimes */
3561592Srgrimes
3571592Srgrimes#include <dev/isp/ispreg.h>
3581592Srgrimes#include <dev/isp/ispvar.h>
3591592Srgrimes#include <dev/isp/ispmbox.h>
3601592Srgrimes
3611592Srgrimesvoid isp_prt(struct ispsoftc *, int level, const char *, ...)
3621592Srgrimes	__printflike(3, 4);
3631592Srgrimes/*
3641592Srgrimes * isp_osinfo definiitions && shorthand
3651592Srgrimes */
3661592Srgrimes#define	SIMQFRZ_RESOURCE	0x1
3671592Srgrimes#define	SIMQFRZ_LOOPDOWN	0x2
3681592Srgrimes#define	SIMQFRZ_TIMED		0x4
3691592Srgrimes
3701592Srgrimes#define	isp_sim		isp_osinfo.sim
3711592Srgrimes#define	isp_path	isp_osinfo.path
3721592Srgrimes#define	isp_sim2	isp_osinfo.sim2
3731592Srgrimes#define	isp_path2	isp_osinfo.path2
3741592Srgrimes#define	isp_dev		isp_osinfo.dev
3751592Srgrimes
3761592Srgrimes/*
3771592Srgrimes * prototypes for isp_pci && isp_freebsd to share
3781592Srgrimes */
3791592Srgrimesextern void isp_attach(struct ispsoftc *);
3801592Srgrimesextern void isp_uninit(struct ispsoftc *);
3811592Srgrimes
3821592Srgrimes/*
3831592Srgrimes * driver global data
3841592Srgrimes */
3851592Srgrimesextern int isp_announced;
3861592Srgrimes
3871592Srgrimes/*
3881592Srgrimes * Platform private flags
3891592Srgrimes */
3901592Srgrimes#define	ISP_SPRIV_ERRSET	0x1
39190377Simp#define	ISP_SPRIV_INWDOG	0x2
3921592Srgrimes#define	ISP_SPRIV_GRACE		0x4
39327074Ssteve#define	ISP_SPRIV_DONE		0x8
3941592Srgrimes
39527079Ssteve#define	XS_CMD_S_WDOG(sccb)	(sccb)->ccb_h.spriv_field0 |= ISP_SPRIV_INWDOG
39627079Ssteve#define	XS_CMD_C_WDOG(sccb)	(sccb)->ccb_h.spriv_field0 &= ~ISP_SPRIV_INWDOG
3971592Srgrimes#define	XS_CMD_WDOG_P(sccb)	((sccb)->ccb_h.spriv_field0 & ISP_SPRIV_INWDOG)
3981592Srgrimes
3991592Srgrimes#define	XS_CMD_S_GRACE(sccb)	(sccb)->ccb_h.spriv_field0 |= ISP_SPRIV_GRACE
400229780Suqs#define	XS_CMD_C_GRACE(sccb)	(sccb)->ccb_h.spriv_field0 &= ~ISP_SPRIV_GRACE
4011592Srgrimes#define	XS_CMD_GRACE_P(sccb)	((sccb)->ccb_h.spriv_field0 & ISP_SPRIV_GRACE)
4021592Srgrimes
4031592Srgrimes#define	XS_CMD_S_DONE(sccb)	(sccb)->ccb_h.spriv_field0 |= ISP_SPRIV_DONE
4041592Srgrimes#define	XS_CMD_C_DONE(sccb)	(sccb)->ccb_h.spriv_field0 &= ~ISP_SPRIV_DONE
4051592Srgrimes#define	XS_CMD_DONE_P(sccb)	((sccb)->ccb_h.spriv_field0 & ISP_SPRIV_DONE)
4061592Srgrimes
4071592Srgrimes#define	XS_CMD_S_CLEAR(sccb)	(sccb)->ccb_h.spriv_field0 = 0
4081592Srgrimes/*
4091592Srgrimes * Platform specific inline functions
4101592Srgrimes */
4111592Srgrimes
4121592Srgrimesstatic INLINE void isp_mbox_wait_complete(struct ispsoftc *);
4131592Srgrimesstatic INLINE void
4141592Srgrimesisp_mbox_wait_complete(struct ispsoftc *isp)
4151592Srgrimes{
4161592Srgrimes	if (isp->isp_osinfo.intsok) {
4171592Srgrimes		int lim = ((isp->isp_mbxwrk0)? 120 : 20) * hz;
4181592Srgrimes		isp->isp_osinfo.mboxwaiting = 1;
4191592Srgrimes#ifdef	ISP_SMPLOCK
4201592Srgrimes		(void) msleep(&isp->isp_mbxworkp,
4211592Srgrimes		    &isp->isp_lock, PRIBIO, "isp_mboxwaiting", lim);
4221592Srgrimes#else
42327074Ssteve		(void) tsleep(&isp->isp_mbxworkp,
42427074Ssteve		    PRIBIO, "isp_mboxwaiting", lim);
42527074Ssteve#endif
4261592Srgrimes		if (isp->isp_mboxbsy != 0) {
4271592Srgrimes			isp_prt(isp, ISP_LOGWARN,
4281592Srgrimes			    "Interrupting Mailbox Command (0x%x) Timeout",
4291592Srgrimes			    isp->isp_lastmbxcmd);
4301592Srgrimes			isp->isp_mboxbsy = 0;
4311592Srgrimes		}
4321592Srgrimes		isp->isp_osinfo.mboxwaiting = 0;
4331592Srgrimes	} else {
4341592Srgrimes		int lim = ((isp->isp_mbxwrk0)? 240 : 60) * 10000;
4351592Srgrimes		int j;
4361592Srgrimes		for (j = 0; j < lim; j++) {
4371592Srgrimes			u_int16_t isr, sema, mbox;
4381592Srgrimes			if (isp->isp_mboxbsy == 0) {
4391592Srgrimes				break;
4401592Srgrimes			}
44127074Ssteve			if (ISP_READ_ISR(isp, &isr, &sema, &mbox)) {
44227074Ssteve				isp_intr(isp, isr, sema, mbox);
4431592Srgrimes				if (isp->isp_mboxbsy == 0) {
4441592Srgrimes					break;
4451592Srgrimes				}
4461592Srgrimes			}
4471592Srgrimes			USEC_DELAY(500);
44868895Skris		}
4491592Srgrimes		if (isp->isp_mboxbsy != 0) {
4501592Srgrimes			isp_prt(isp, ISP_LOGWARN,
4511592Srgrimes			    "Polled Mailbox Command (0x%x) Timeout",
4521592Srgrimes			    isp->isp_lastmbxcmd);
4531592Srgrimes		}
4541592Srgrimes	}
4551592Srgrimes}
4561592Srgrimes
4571592Srgrimesstatic INLINE u_int64_t nanotime_sub(struct timespec *, struct timespec *);
4581592Srgrimesstatic INLINE u_int64_t
4591592Srgrimesnanotime_sub(struct timespec *b, struct timespec *a)
46027074Ssteve{
4611592Srgrimes	u_int64_t elapsed;
4621592Srgrimes	struct timespec x = *b;
4631592Srgrimes	timespecsub(&x, a);
4641592Srgrimes	elapsed = GET_NANOSEC(&x);
4651592Srgrimes	if (elapsed == 0)
4661592Srgrimes		elapsed++;
4671592Srgrimes	return (elapsed);
4681592Srgrimes}
4691592Srgrimes
4701592Srgrimesstatic INLINE char *strncat(char *, const char *, size_t);
4711592Srgrimesstatic INLINE char *
4721592Srgrimesstrncat(char *d, const char *s, size_t c)
4731592Srgrimes{
4741592Srgrimes        char *t = d;
4751592Srgrimes
4761592Srgrimes        if (c) {
4771592Srgrimes                while (*d)
4781592Srgrimes                        d++;
4791592Srgrimes                while ((*d++ = *s++)) {
4801592Srgrimes                        if (--c == 0) {
4811592Srgrimes                                *d = '\0';
4821592Srgrimes                                break;
4831592Srgrimes                        }
4841592Srgrimes                }
4851592Srgrimes        }
4861592Srgrimes        return (t);
4871592Srgrimes}
4881592Srgrimes
4891592Srgrimes/*
4901592Srgrimes * Common inline functions
4911592Srgrimes */
4921592Srgrimes
4931592Srgrimes#include <dev/isp/isp_inline.h>
4941592Srgrimes#endif	/* _ISP_FREEBSD_H */
4951592Srgrimes