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/scsipi/scsipiconf.c

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 /*      $NetBSD: scsipiconf.c,v 1.45 2019/03/28 10:44:29 kardel Exp $   */
    2 
    3 /*-
    4  * Copyright (c) 1998, 1999, 2004 The NetBSD Foundation, Inc.
    5  * All rights reserved.
    6  *
    7  * This code is derived from software contributed to The NetBSD Foundation
    8  * by Charles M. Hannum; by Jason R. Thorpe of the Numerical Aerospace
    9  * Simulation Facility, NASA Ames Research Center.
   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 /*
   34  * Originally written by Julian Elischer (julian@tfs.com)
   35  * for TRW Financial Systems for use under the MACH(2.5) operating system.
   36  *
   37  * TRW Financial Systems, in accordance with their agreement with Carnegie
   38  * Mellon University, makes this software available to CMU to distribute
   39  * or use in any manner that they see fit as long as this message is kept with
   40  * the software. For this reason TFS also grants any other persons or
   41  * organisations permission to use or modify this software.
   42  *
   43  * TFS supplies this software to be publicly redistributed
   44  * on the understanding that TFS is not responsible for the correct
   45  * functioning of this software in any circumstances.
   46  *
   47  * Ported to run under 386BSD by Julian Elischer (julian@tfs.com) Sept 1992
   48  */
   49 
   50 #include <sys/cdefs.h>
   51 __KERNEL_RCSID(0, "$NetBSD: scsipiconf.c,v 1.45 2019/03/28 10:44:29 kardel Exp $");
   52 
   53 #include <sys/param.h>
   54 #include <sys/systm.h>
   55 #include <sys/malloc.h>
   56 #include <sys/module.h>
   57 #include <sys/device.h>
   58 #include <sys/proc.h>
   59 
   60 #include <dev/scsipi/scsipi_all.h>
   61 #include <dev/scsipi/scsipiconf.h>
   62 #include <dev/scsipi/scsipi_base.h>
   63 
   64 
   65 /* Function pointers and stub routines for scsiverbose module */
   66 int (*scsipi_print_sense)(struct scsipi_xfer *, int) = scsipi_print_sense_stub;
   67 void (*scsipi_print_sense_data)(struct scsi_sense_data *, int) =
   68                 scsipi_print_sense_data_stub;
   69 
   70 int scsi_verbose_loaded = 0; 
   71 
   72 int
   73 scsipi_print_sense_stub(struct scsipi_xfer * xs, int verbosity)
   74 {
   75         scsipi_load_verbose();
   76         if (scsi_verbose_loaded)
   77                 return scsipi_print_sense(xs, verbosity);
   78         else
   79                 return 0;
   80 }
   81 
   82 void
   83 scsipi_print_sense_data_stub(struct scsi_sense_data *sense, int verbosity)
   84 {
   85         scsipi_load_verbose();
   86         if (scsi_verbose_loaded)
   87                 scsipi_print_sense_data(sense, verbosity);
   88 }
   89 
   90 int
   91 scsipi_command(struct scsipi_periph *periph, struct scsipi_generic *cmd,
   92     int cmdlen, u_char *data_addr, int datalen, int retries, int timeout,
   93     struct buf *bp, int flags)
   94 {
   95         struct scsipi_xfer *xs;
   96         int rc;
   97 
   98         /*
   99          * execute unlocked to allow waiting for memory
  100          */
  101         xs = scsipi_make_xs_unlocked(periph, cmd, cmdlen, data_addr, datalen, retries,
  102             timeout, bp, flags);
  103         if (!xs)
  104                 return (ENOMEM);
  105 
  106         mutex_enter(chan_mtx(periph->periph_channel));
  107         rc = scsipi_execute_xs(xs);
  108         mutex_exit(chan_mtx(periph->periph_channel));
  109 
  110         return rc;
  111 }
  112 
  113 /* 
  114  * Load the scsiverbose module
  115  */   
  116 void
  117 scsipi_load_verbose(void)
  118 {
  119         if (scsi_verbose_loaded == 0)
  120                 module_autoload("scsiverbose", MODULE_CLASS_MISC);
  121 }
  122 
  123 /*
  124  * allocate and init a scsipi_periph structure for a new device.
  125  */
  126 struct scsipi_periph *
  127 scsipi_alloc_periph(int malloc_flag)
  128 {
  129         struct scsipi_periph *periph;
  130         u_int i;
  131 
  132         periph = malloc(sizeof(*periph), M_DEVBUF, malloc_flag|M_ZERO);
  133         if (periph == NULL)
  134                 return NULL;
  135 
  136         periph->periph_dev = NULL;
  137         periph->periph_opcs = NULL;
  138 
  139         /*
  140          * Start with one command opening.  The periph driver
  141          * will grow this if it knows it can take advantage of it.
  142          */
  143         periph->periph_openings = 1;
  144         periph->periph_active = 0;
  145 
  146         for (i = 0; i < PERIPH_NTAGWORDS; i++)
  147                 periph->periph_freetags[i] = 0xffffffff;
  148 
  149         TAILQ_INIT(&periph->periph_xferq);
  150         callout_init(&periph->periph_callout, 0);
  151         cv_init(&periph->periph_cv, "periph");
  152 
  153         return periph;
  154 }
  155 
  156 /*
  157  * cleanup and free scsipi_periph structure
  158  */
  159 void
  160 scsipi_free_periph(struct scsipi_periph *periph)
  161 {
  162         scsipi_free_opcodeinfo(periph);
  163         cv_destroy(&periph->periph_cv);
  164         free(periph, M_DEVBUF);
  165 }
  166 
  167 /*
  168  * Return a priority based on how much of the inquiry data matches
  169  * the patterns for the particular driver.
  170  */
  171 const void *
  172 scsipi_inqmatch(struct scsipi_inquiry_pattern *inqbuf, const void *base,
  173     size_t nmatches, size_t matchsize, int *bestpriority)
  174 {
  175         u_int8_t type;
  176         const struct scsipi_inquiry_pattern *bestmatch;
  177 
  178         /* Include the qualifier to catch vendor-unique types. */
  179         type = inqbuf->type;
  180 
  181         for (*bestpriority = 0, bestmatch = 0; nmatches--;
  182             base = (const char *)base + matchsize) {
  183                 const struct scsipi_inquiry_pattern *match = base;
  184                 int priority, len;
  185 
  186                 if (type != match->type)
  187                         continue;
  188                 if (inqbuf->removable != match->removable)
  189                         continue;
  190                 priority = 2;
  191                 len = strlen(match->vendor);
  192                 if (memcmp(inqbuf->vendor, match->vendor, len))
  193                         continue;
  194                 priority += len;
  195                 len = strlen(match->product);
  196                 if (memcmp(inqbuf->product, match->product, len))
  197                         continue;
  198                 priority += len;
  199                 len = strlen(match->revision);
  200                 if (memcmp(inqbuf->revision, match->revision, len))
  201                         continue;
  202                 priority += len;
  203 
  204 #ifdef SCSIPI_DEBUG
  205                 printf("scsipi_inqmatch: %d/%d/%d <%s, %s, %s>\n",
  206                     priority, match->type, match->removable,
  207                     match->vendor, match->product, match->revision);
  208 #endif
  209                 if (priority > *bestpriority) {
  210                         *bestpriority = priority;
  211                         bestmatch = base;
  212                 }
  213         }
  214 
  215         return (bestmatch);
  216 }
  217 
  218 const char *
  219 scsipi_dtype(int type)
  220 {
  221         const char *dtype;
  222 
  223         switch (type) {
  224         case T_DIRECT:
  225                 dtype = "disk";
  226                 break;
  227         case T_SEQUENTIAL:
  228                 dtype = "tape";
  229                 break;
  230         case T_PRINTER:
  231                 dtype = "printer";
  232                 break;
  233         case T_PROCESSOR:
  234                 dtype = "processor";
  235                 break;
  236         case T_WORM:
  237                 dtype = "worm";
  238                 break;
  239         case T_CDROM:
  240                 dtype = "cdrom";
  241                 break;
  242         case T_SCANNER:
  243                 dtype = "scanner";
  244                 break;
  245         case T_OPTICAL:
  246                 dtype = "optical";
  247                 break;
  248         case T_CHANGER:
  249                 dtype = "changer";
  250                 break;
  251         case T_COMM:
  252                 dtype = "communication";
  253                 break;
  254         case T_IT8_1:
  255         case T_IT8_2:
  256                 dtype = "graphic arts pre-press";
  257                 break;
  258         case T_STORARRAY:
  259                 dtype = "storage array";
  260                 break;
  261         case T_ENCLOSURE:
  262                 dtype = "enclosure services";
  263                 break;
  264         case T_SIMPLE_DIRECT:
  265                 dtype = "simplified direct";
  266                 break;
  267         case T_OPTIC_CARD_RW:
  268                 dtype = "optical card r/w";
  269                 break;
  270         case T_OBJECT_STORED:
  271                 dtype = "object-based storage";
  272                 break;
  273         case T_NODEVICE:
  274                 panic("scsipi_dtype: impossible device type");
  275         default:
  276                 dtype = "unknown";
  277                 break;
  278         }
  279         return (dtype);
  280 }

Cache object: a2cbaac8242b449e77dcc30d6143cceb


[ 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.