The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/dev/ic/wdcvar.h

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*      $OpenBSD: wdcvar.h,v 1.57 2022/01/09 05:42:42 jsg Exp $     */
    2 /*      $NetBSD: wdcvar.h,v 1.17 1999/04/11 20:50:29 bouyer Exp $       */
    3 
    4 /*-
    5  * Copyright (c) 1998 The NetBSD Foundation, Inc.
    6  * All rights reserved.
    7  *
    8  * This code is derived from software contributed to The NetBSD Foundation
    9  * by Charles M. Hannum, by Onno van der Linden and by Manuel Bouyer.
   10  *
   11  * Redistribution and use in source and binary forms, with or without
   12  * modification, are permitted provided that the following conditions
   13  * are met:
   14  * 1. Redistributions of source code must retain the above copyright
   15  *      notice, this list of conditions and the following disclaimer.
   16  * 2. Redistributions in binary form must reproduce the above copyright
   17  *      notice, this list of conditions and the following disclaimer in the
   18  *      documentation and/or other materials provided with the distribution.
   19  *
   20  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
   21  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
   22  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
   23  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
   24  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
   25  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
   26  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
   27  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
   28  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
   29  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
   30  * POSSIBILITY OF SUCH DAMAGE.
   31  */
   32 
   33 #ifndef _DEV_IC_WDCVAR_H_
   34 #define _DEV_IC_WDCVAR_H_
   35 
   36 #include <sys/timeout.h>
   37 
   38 struct channel_queue {  /* per channel queue (may be shared) */
   39         TAILQ_HEAD(xferhead, wdc_xfer) sc_xfer;
   40 };
   41 
   42 struct channel_softc_vtbl;
   43 
   44 
   45 #define WDC_OPTION_PROBE_VERBOSE   0x10000
   46 
   47 struct channel_softc { /* Per channel data */
   48         struct channel_softc_vtbl  *_vtbl;
   49 
   50         /* Our location */
   51         int channel;
   52         /* Our controller's softc */
   53         struct wdc_softc *wdc;
   54         /* Our registers */
   55         bus_space_tag_t       cmd_iot;
   56         bus_space_handle_t    cmd_ioh;
   57         bus_size_t            cmd_iosz;
   58         bus_space_tag_t       ctl_iot;
   59         bus_space_handle_t    ctl_ioh;
   60         bus_size_t            ctl_iosz;
   61         /* data32{iot,ioh} are only used for 32 bit xfers */
   62         bus_space_tag_t         data32iot;
   63         bus_space_handle_t      data32ioh;
   64         /* Our state */
   65         int ch_flags;
   66 #define WDCF_ACTIVE             0x01 /* channel is active */
   67 #define WDCF_ONESLAVE           0x02 /* slave-only channel */
   68 #define WDCF_IRQ_WAIT           0x10 /* controller is waiting for irq */
   69 #define WDCF_DMA_WAIT           0x20 /* controller is waiting for DMA */
   70 #define WDCF_VERBOSE_PROBE      0x40 /* verbose probe */
   71 #define WDCF_DMA_BEFORE_CMD     0x80 /* start dma before a command */
   72         u_int8_t ch_status;         /* copy of status register */
   73         u_int8_t ch_prev_log_status; /* previous logged value of status reg */
   74         u_int8_t ch_log_idx;
   75         u_int8_t ch_error;          /* copy of error register */
   76         /* per-drive infos */
   77         struct ata_drive_datas ch_drive[2];
   78 
   79         /*
   80          * channel queues. May be the same for all channels, if hw channels
   81          * are not independent.
   82          */
   83         struct channel_queue *ch_queue;
   84         struct timeout ch_timo;
   85 
   86         int dying;
   87 };
   88 
   89 /*
   90  * Disk Controller register definitions.
   91  */
   92 #define _WDC_REGMASK 7
   93 #define _WDC_AUX     8
   94 #define _WDC_RDONLY  16
   95 #define _WDC_WRONLY  32
   96 enum wdc_regs {
   97         wdr_error = _WDC_RDONLY | 1,
   98         wdr_features = _WDC_WRONLY | 1,
   99         wdr_seccnt = 2,
  100         wdr_ireason = 2,
  101         wdr_sector = 3,
  102         wdr_lba_lo = 3,
  103         wdr_cyl_lo = 4,
  104         wdr_lba_mi = 4,
  105         wdr_cyl_hi = 5,
  106         wdr_lba_hi = 5,
  107         wdr_sdh = 6,
  108         wdr_status = _WDC_RDONLY | 7,
  109         wdr_command = _WDC_WRONLY | 7,
  110         wdr_altsts = _WDC_RDONLY | _WDC_AUX,
  111         wdr_ctlr = _WDC_WRONLY | _WDC_AUX
  112 };
  113 
  114 #define WDC_NREG        8 /* number of command registers */
  115 #define WDC_NSHADOWREG  2 /* number of command "shadow" registers */
  116 
  117 struct channel_softc_vtbl {
  118         u_int8_t (*read_reg)(struct channel_softc *, enum wdc_regs reg);
  119         void (*write_reg)(struct channel_softc *, enum wdc_regs reg,
  120             u_int8_t var);
  121         void (*lba48_write_reg)(struct channel_softc *, enum wdc_regs reg,
  122             u_int16_t var);
  123 
  124         void (*read_raw_multi_2)(struct channel_softc *,
  125             void *data, unsigned int nbytes);
  126         void (*write_raw_multi_2)(struct channel_softc *,
  127             void *data, unsigned int nbytes);
  128 
  129         void (*read_raw_multi_4)(struct channel_softc *,
  130             void *data, unsigned int nbytes);
  131         void (*write_raw_multi_4)(struct channel_softc *,
  132             void *data, unsigned int nbytes);
  133 };
  134 
  135 
  136 #define CHP_READ_REG(chp, a)  ((chp)->_vtbl->read_reg)(chp, a)
  137 #define CHP_WRITE_REG(chp, a, b)  ((chp)->_vtbl->write_reg)(chp, a, b)
  138 #define CHP_LBA48_WRITE_REG(chp, a, b)  \
  139         ((chp)->_vtbl->lba48_write_reg)(chp, a, b)
  140 
  141 #define CHP_READ_RAW_MULTI_2(chp, a, b)  \
  142         ((chp)->_vtbl->read_raw_multi_2)(chp, a, b)
  143 #define CHP_WRITE_RAW_MULTI_2(chp, a, b)  \
  144         ((chp)->_vtbl->write_raw_multi_2)(chp, a, b)
  145 #define CHP_READ_RAW_MULTI_4(chp, a, b)  \
  146         ((chp)->_vtbl->read_raw_multi_4)(chp, a, b)
  147 #define CHP_WRITE_RAW_MULTI_4(chp, a, b)  \
  148         ((chp)->_vtbl->write_raw_multi_4)(chp, a, b)
  149 
  150 struct wdc_softc { /* Per controller state */
  151         struct device sc_dev;
  152         /* mandatory fields */
  153         int           cap;
  154 /* Capabilities supported by the controller */
  155 #define WDC_CAPABILITY_DATA16 0x0001    /* can do  16-bit data access */
  156 #define WDC_CAPABILITY_DATA32 0x0002    /* can do 32-bit data access */
  157 #define WDC_CAPABILITY_MODE   0x0004    /* controller knows its PIO/DMA modes */
  158 #define WDC_CAPABILITY_DMA    0x0008    /* DMA */
  159 #define WDC_CAPABILITY_UDMA   0x0010    /* Ultra-DMA/33 */
  160 #define WDC_CAPABILITY_NO_EXTRA_RESETS 0x0100 /* only reset once */
  161 #define WDC_CAPABILITY_PREATA 0x0200    /* ctrl can be a pre-ata one */
  162 #define WDC_CAPABILITY_IRQACK 0x0400    /* callback to ack interrupt */
  163 #define WDC_CAPABILITY_SINGLE_DRIVE 0x800 /* Don't probe second drive */
  164 #define WDC_CAPABILITY_NO_ATAPI_DMA 0x1000 /* Don't do DMA with ATAPI */
  165 #define WDC_CAPABILITY_SATA   0x2000    /* SATA controller */
  166         u_int8_t      PIO_cap; /* highest PIO mode supported */
  167         u_int8_t      DMA_cap; /* highest DMA mode supported */
  168         u_int8_t      UDMA_cap; /* highest UDMA mode supported */
  169         int nchannels;  /* Number of channels on this controller */
  170         struct channel_softc **channels;  /* channel-specific data (array) */
  171         u_int16_t quirks;               /* per-device oddities */
  172 #define WDC_QUIRK_NOSHORTDMA    0x0001  /* can't do short DMA transfers */
  173 #define WDC_QUIRK_NOATA         0x0002  /* skip attaching ATA disks */
  174 #define WDC_QUIRK_NOATAPI       0x0004  /* skip attaching ATAPI devices */
  175 
  176 #if 0
  177         /*
  178          * The reference count here is used for both IDE and ATAPI devices.
  179          */
  180         struct scsipi_adapter sc_atapi_adapter;
  181 #endif
  182 
  183         /* if WDC_CAPABILITY_DMA set in 'cap' */
  184         void            *dma_arg;
  185         int            (*dma_init)(void *, int, int, void *, size_t,
  186                         int);
  187         void           (*dma_start)(void *, int, int);
  188         int            (*dma_finish)(void *, int, int, int);
  189 /* flags passed to DMA functions */
  190 #define WDC_DMA_READ    0x01
  191 #define WDC_DMA_IRQW    0x02
  192 #define WDC_DMA_LBA48   0x04
  193         int             dma_status; /* status return from dma_finish() */
  194 #define WDC_DMAST_NOIRQ 0x01 /* missing IRQ */
  195 #define WDC_DMAST_ERR   0x02 /* DMA error */
  196 #define WDC_DMAST_UNDER 0x04 /* DMA underrun */
  197 
  198         /* if WDC_CAPABILITY_MODE set in 'cap' */
  199         void            (*set_modes)(struct channel_softc *);
  200 
  201         /* if WDC_CAPABILITY_IRQACK set in 'cap' */
  202         void            (*irqack)(struct channel_softc *);
  203 
  204         void            (*reset)(struct channel_softc *);
  205 
  206         /* Driver callback to probe for drives */
  207         void (*drv_probe)(struct channel_softc *);
  208 };
  209 
  210  /*
  211   * Description of a command to be handled by a controller.
  212   * These commands are queued in a list.
  213   */
  214 struct atapi_return_args;
  215 
  216 struct wdc_xfer {
  217         volatile u_int c_flags;
  218 #define C_ATAPI         0x0002 /* xfer is ATAPI request */
  219 #define C_TIMEOU        0x0004 /* xfer processing timed out */
  220 #define C_NEEDDONE      0x0010 /* need to call upper-level done */
  221 #define C_POLL          0x0020 /* cmd is polled */
  222 #define C_DMA           0x0040 /* cmd uses DMA */
  223 #define C_SENSE         0x0080 /* cmd is a internal command */
  224 #define C_MEDIA_ACCESS  0x0100 /* is a media access command */
  225 #define C_POLL_MACHINE  0x0200 /* machine has a poll handler */
  226 #define C_PRIVATEXFER   0x0400 /* privately managed xfer */
  227 #define C_SCSIXFER      0x0800 /* SCSI managed xfer */
  228 
  229         /* Information about our location */
  230         struct channel_softc *chp;
  231         u_int8_t drive;
  232 
  233         /* Information about the current transfer  */
  234         void *cmd; /* wdc, ata or scsipi command structure */
  235         void *databuf;
  236         int c_bcount;      /* byte count left */
  237         int c_skip;        /* bytes already transferred */
  238         TAILQ_ENTRY(wdc_xfer) c_xferchain;
  239         LIST_ENTRY(wdc_xfer) free_list;
  240         void (*c_start)(struct channel_softc *, struct wdc_xfer *);
  241         int  (*c_intr)(struct channel_softc *, struct wdc_xfer *, int);
  242         void (*c_kill_xfer)(struct channel_softc *, struct wdc_xfer *);
  243 
  244         /* Used by ATAPISCSI */
  245         volatile int endticks;
  246         struct timeout atapi_poll_to;
  247         void (*next)(struct channel_softc *, struct wdc_xfer *, int,
  248                          struct atapi_return_args *);
  249         void (*c_done)(struct channel_softc *, struct wdc_xfer *, int,
  250                          struct atapi_return_args *);
  251 
  252         /* Used for tape devices */
  253         int  transfer_len;
  254 };
  255 
  256 /*
  257  * Public functions which can be called by ATA or ATAPI specific parts,
  258  * or bus-specific backends.
  259  */
  260 
  261 int   wdcprobe(struct channel_softc *);
  262 void  wdcattach(struct channel_softc *);
  263 int   wdcdetach(struct channel_softc *, int);
  264 int   wdcintr(void *);
  265 struct channel_queue *wdc_alloc_queue(void);
  266 void  wdc_free_queue(struct channel_queue *);
  267 void  wdc_exec_xfer(struct channel_softc *, struct wdc_xfer *);
  268 struct wdc_xfer *wdc_get_xfer(int); /* int = WDC_NOSLEEP/CANSLEEP */
  269 #define WDC_CANSLEEP    0x00
  270 #define WDC_NOSLEEP     0x01
  271 void   wdc_scrub_xfer(struct wdc_xfer *);
  272 void   wdc_free_xfer(struct channel_softc *, struct wdc_xfer *);
  273 void  wdcstart(struct channel_softc *);
  274 int   wdcreset(struct channel_softc *, int);
  275 #define NOWAIT  0x02
  276 #define VERBOSE 0x01
  277 #define SILENT  0x00 /* wdcreset will not print errors */
  278 int   wdc_wait_for_status(struct channel_softc *, int, int, int);
  279 int   wdc_dmawait(struct channel_softc *, struct wdc_xfer *, int);
  280 void  wdcbit_bucket(struct channel_softc *, int);
  281 
  282 void  wdccommand(struct channel_softc *, u_int8_t, u_int8_t, u_int16_t,
  283         u_int8_t, u_int8_t, u_int8_t, u_int8_t);
  284 void  wdccommandext(struct channel_softc *, u_int8_t, u_int8_t, u_int64_t,
  285         u_int16_t);
  286 void  wdccommandshort(struct channel_softc *, int, int);
  287 void  wdctimeout(void *arg);
  288 void  wdc_do_reset(struct channel_softc *);
  289 
  290 int   wdc_addref(struct channel_softc *);
  291 void  wdc_delref(struct channel_softc *);
  292 
  293 /*
  294  * ST506 spec says that if READY or SEEKCMPLT go off, then the read or write
  295  * command is aborted.
  296  */
  297 #define wdcwait(chp, status, mask, timeout) ((wdc_wait_for_status((chp), (status), (mask), (timeout)) >= 0) ? 0 : -1)
  298 #define wait_for_drq(chp, timeout) wdcwait((chp), WDCS_DRQ, WDCS_DRQ, (timeout))
  299 #define wait_for_unbusy(chp, timeout) wdcwait((chp), 0, 0, (timeout))
  300 #define wait_for_ready(chp, timeout) wdcwait((chp), WDCS_DRDY, \
  301         WDCS_DRDY, (timeout))
  302 
  303 /* ATA/ATAPI specs says a device can take 31s to reset */
  304 #define WDC_RESET_WAIT 31000
  305 
  306 void wdc_disable_intr(struct channel_softc *);
  307 void wdc_enable_intr(struct channel_softc *);
  308 int wdc_select_drive(struct channel_softc *, int, int);
  309 void wdc_set_drive(struct channel_softc *, int drive);
  310 void wdc_output_bytes(struct ata_drive_datas *drvp, void *, unsigned int);
  311 void wdc_input_bytes(struct ata_drive_datas *drvp, void *, unsigned int);
  312 
  313 void wdc_print_current_modes(struct channel_softc *);
  314 
  315 int wdc_ioctl(struct ata_drive_datas *, u_long, caddr_t, int, struct proc *);
  316 
  317 u_int8_t wdc_default_read_reg(struct channel_softc *,
  318                 enum wdc_regs);
  319 void     wdc_default_write_reg(struct channel_softc *,
  320                 enum wdc_regs, u_int8_t);
  321 void     wdc_default_lba48_write_reg(struct channel_softc *,
  322                 enum wdc_regs, u_int16_t);
  323 void     wdc_default_read_raw_multi_2(struct channel_softc *,
  324                 void *, unsigned int);
  325 void     wdc_default_write_raw_multi_2(struct channel_softc *,
  326                 void *, unsigned int);
  327 void     wdc_default_read_raw_multi_4(struct channel_softc *,
  328                 void *, unsigned int);
  329 void     wdc_default_write_raw_multi_4(struct channel_softc *,
  330                 void *, unsigned int);
  331 
  332 #endif  /* !_DEV_IC_WDCVAR_H_ */

Cache object: 3d24e8ebc06bf770de74b9cf56e17a0f


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.