TRAN_INIT_PKT(9E) Driver Entry Points TRAN_INIT_PKT(9E)
NAME
tran_init_pkt, tran_destroy_pkt - SCSI HBA packet preparation and
deallocation
SYNOPSIS
#include <sys/scsi/scsi.h>
struct scsi_pkt *prefixtran_init_pkt(
struct scsi_address *ap,
struct scsi_pkt *pkt,
struct buf *bp,
int cmdlen,
int statuslen,
int tgtlen,
intflags,
int (*callback,
caddr_t),caddr_t arg);
void prefixtran_destroy_pkt(
struct scsi_address *ap,
struct scsi_pkt *pkt);
INTERFACE LEVEL
illumos architecture specific (illumos DDI).
PARAMETERS
ap Pointer to a
scsi_address(9S) structure.
pkt Pointer to a
scsi_pkt(9S) structure allocated in an earlier
call, or
NULL.
bp Pointer to a
buf(9S) structure if
DMA resources are to be
allocated for the
pkt, or
NULL.
cmdlen The required length for the
SCSI command descriptor block
(
CDB) in bytes.
statuslen The required length for the
SCSI status completion block
(
SCB) in bytes.
tgtlen The length of the packet private area within the
scsi_pkt to
be allocated on behalf of the
SCSI target driver.
flags Flags for creating the packet.
callback Pointer to either
NULL_FUNC or
SLEEP_FUNC.
arg Always
NULL.
DESCRIPTION
The
tran_init_pkt() and
tran_destroy_pkt() vectors in the
scsi_hba_tran structure must be initialized during the
HBA driver's
attach(9E) to point
to
HBA entry points to be called when a target driver calls
scsi_init_pkt(9F) and
scsi_destroy_pkt(9F).
tran_init_pkt() tran_init_pkt() is the entry point into the
HBA which is used to allocate
and initialize a
scsi_pkt structure on behalf of a
SCSI target driver. If
pkt is
NULL, the
HBA driver must use
scsi_hba_pkt_alloc(9F) to allocate a
new
scsi_pkt structure.
If
bp is non-
NULL, the
HBA driver must allocate appropriate
DMA resources
for the
pkt, for example, through
ddi_dma_buf_setup(9F) or
ddi_dma_buf_bind_handle(9F).
If the
PKT_CONSISTENT bit is set in
flags, the buffer was allocated by
scsi_alloc_consistent_buf(9F). For packets marked with
PKT_CONSISTENT, the
HBA driver must synchronize any cached data transfers before calling
the target driver's command completion callback.
If the
PKT_DMA_PARTIAL bit is set in
flags, the
HBA driver should set up
partial data transfers, such as setting the
DDI_DMA_PARTIAL bit in the
flags argument if interfaces such as
ddi_dma_buf_setup(9F) or
ddi_dma_buf_bind_handle(9F) are used.
If only partial
DMA resources are available,
tran_init_pkt() must return
in the
pkt_resid field of
pkt the number of bytes of
DMA resources not
allocated.
If both
pkt and
bp are non-
NULL, if the
PKT_DMA_PARTIAL bit is set in
flags, and if
DMA resources have already been allocated for the pkt with
a previous call to
tran_init_pkt() that returned a non-zero
pkt_resid field, this request is to move the
DMA resources for the subsequent piece
of the transfer.
The contents of
scsi_address(9S) pointed to by
ap are copied into the
pkt_address field of the
scsi_pkt(9S) by
scsi_hba_pkt_alloc(9F).
tgtlen is the length of the packet private area in the
scsi_pkt structure
to be allocated on behalf of the
SCSI target driver.
statuslen is the required length for the
SCSI status completion block.
If the requested status length is greater than or equal to
sizeof(struct scsi_arq_status) and the
auto_rqsense capability has been set,
automatic request sense (
ARS) is enabled for this packet. If the status
length is less than
sizeof(struct scsi_arq_status), automatic request
sense must be disabled for this
pkt.
If the
HBA driver is not capable of disabling
ARQ on a per-packet basis
and
tran_init_pkt() is called with a
statuslen that is less than
sizeof(struct scsi_arq_status), the driver's
tran_init_pkt routine should
allocate at least
sizeof(struct scsi_arq_status). If an
ARS is needed,
upon successful
ARS done by the
HBA driver, the driver must copy the
sense data over and set
STAT_ARQ_DONE in
pkt_state.
cmdlen is the required length for the
SCSI command descriptor block.
Note:
tgtlen,
statuslen, and
cmdlen are used only when the
HBA driver
allocates the
scsi_pkt(9S), in other words, when
pkt is
NULL.
callback indicates what the allocator routines should do when resources
are not available:
NULL_FUNC Do not wait for resources. Return a
NULL pointer.
SLEEP_FUNC Wait indefinitely for resources.
tran_destroy_pkt() tran_destroy_pkt() is the entry point into the
HBA that must free all of
the resources that were allocated to the
scsi_pkt(9S) structure during
tran_init_pkt().
RETURN VALUES
tran_init_pkt() must return a pointer to a
scsi_pkt(9S) structure on
success, or
NULL on failure.
If
pkt is
NULL on entry, and
tran_init_pkt() allocated a packet through
scsi_hba_pkt_alloc(9F) but was unable to allocate
DMA resources,
tran_init_pkt() must free the packet through
scsi_hba_pkt_free(9F) before
returning
NULL.
SEE ALSO
attach(9E),
tran_setup_pkt(9E),
tran_sync_pkt(9E),
biodone(9F),
bioerror(9F),
ddi_dma_buf_bind_handle(9F),
ddi_dma_buf_setup(9F),
kmem_cache_create(9F),
scsi_alloc_consistent_buf(9F),
scsi_destroy_pkt(9F),
scsi_hba_attach(9F),
scsi_hba_pkt_alloc(9F),
scsi_hba_pkt_free(9F),
scsi_init_pkt(9F),
buf(9S),
scsi_address(9S),
scsi_hba_tran(9S),
scsi_pkt(9S) Writing Device DriversNOTES
If a
DMA allocation request fails with
DDI_DMA_NOMAPPING, indicate the
error by calling
bioerror(9F) with
bp and an error code of
EFAULT.
If a
DMA allocation request fails with
DDI_DMA_TOOBIG, indicate the error
by calling
bioerror(9F) with
bp and an error code of
EINVAL.
For increased performance, an HBA driver may want to provide a cache for
scsi_pkt(9S) allocation. This cache should be implemented by the HBA
driver providing a
tran_setup_pkt(9E) implementation. Implementing this
cache by direct use of
kmem_cache_create(9F) adds a compile-time
dependency on
scsi_pkt() size, which is illegal.
January 11, 2009
TRAN_INIT_PKT(9E)