Date: Wed, 8 Apr 2009 08:12:03 GMT From: Scott Long <scottl@FreeBSD.org> To: Perforce Change Reviews <perforce@freebsd.org> Subject: PERFORCE change 160366 for review Message-ID: <200904080812.n388C3Ks004914@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=160366 Change 160366 by scottl@scottl-deimos on 2009/04/08 08:11:49 Split xpt_alloc_device up and move part of it to scsi_xpt.c, along with xpt_devise_transport. Affected files ... .. //depot/projects/scottl-camlock/src/sys/cam/cam_xpt.c#82 edit .. //depot/projects/scottl-camlock/src/sys/cam/cam_xpt.h#14 edit .. //depot/projects/scottl-camlock/src/sys/cam/scsi/scsi_xpt.c#8 edit Differences ... ==== //depot/projects/scottl-camlock/src/sys/cam/cam_xpt.c#82 (text+ko) ==== @@ -224,9 +224,6 @@ static struct cam_et* xpt_alloc_target(struct cam_eb *bus, target_id_t target_id); static void xpt_release_target(struct cam_eb *bus, struct cam_et *target); -static struct cam_ed* - xpt_alloc_device(struct cam_eb *bus, struct cam_et *target, - lun_id_t lun_id); static void xpt_release_device(struct cam_eb *bus, struct cam_et *target, struct cam_ed *device); static u_int32_t xpt_dev_ccbq_resize(struct cam_path *path, int newopenings); @@ -2644,8 +2641,8 @@ cgds->devq_queued = dev->ccbq.queue.entries; cgds->held = dev->ccbq.held; cgds->last_reset = tar->last_reset; - cgds->maxtags = dev->quirk->maxtags; - cgds->mintags = dev->quirk->mintags; + cgds->maxtags = dev->maxtags; + cgds->mintags = dev->mintags; if (timevalcmp(&tar->last_reset, &bus->last_reset, <)) cgds->last_reset = bus->last_reset; cgds->ccb_h.status = CAM_REQ_CMP; @@ -3460,9 +3457,10 @@ /* Create one */ struct cam_ed *new_device; - new_device = xpt_alloc_device(bus, - target, - lun_id); + new_device = + (*(bus->xport->xpt_alloc_device))(bus, + target, + lun_id); if (new_device == NULL) { status = CAM_RESRC_UNAVAIL; } else { @@ -4365,10 +4363,9 @@ } } -static struct cam_ed * +struct cam_ed * xpt_alloc_device(struct cam_eb *bus, struct cam_et *target, lun_id_t lun_id) { - struct cam_path path; struct cam_ed *device; struct cam_devq *devq; cam_status status; @@ -4385,8 +4382,6 @@ } if (device != NULL) { - struct cam_ed *cur_device; - cam_init_pinfo(&device->alloc_ccb_entry.pinfo); device->alloc_ccb_entry.device = device; cam_init_pinfo(&device->send_ccb_entry.pinfo); @@ -4409,16 +4404,6 @@ SLIST_INIT(&device->periphs); device->generation = 0; device->owner = NULL; - /* - * Take the default quirk entry until we have inquiry - * data and can determine a better quirk to use. - */ - device->quirk = &xpt_quirk_table[xpt_quirk_table_size - 1]; - bzero(&device->inq_data, sizeof(device->inq_data)); - device->inq_flags = 0; - device->queue_flags = 0; - device->serial_num = NULL; - device->serial_num_len = 0; device->qfrozen_cnt = 0; device->flags = CAM_DEV_UNCONFIGURED; device->tag_delay_count = 0; @@ -4435,30 +4420,6 @@ */ target->refcount++; - /* - * XXX should be limited by number of CCBs this bus can - * do. - */ - bus->sim->max_ccbs += device->ccbq.devq_openings; - /* Insertion sort into our target's device list */ - cur_device = TAILQ_FIRST(&target->ed_entries); - while (cur_device != NULL && cur_device->lun_id < lun_id) - cur_device = TAILQ_NEXT(cur_device, links); - if (cur_device != NULL) { - TAILQ_INSERT_BEFORE(cur_device, device, links); - } else { - TAILQ_INSERT_TAIL(&target->ed_entries, device, links); - } - target->generation++; - if (lun_id != CAM_LUN_WILDCARD) { - xpt_compile_path(&path, - NULL, - bus->path_id, - target->target_id, - lun_id); - xpt_devise_transport(&path); - xpt_release_path(&path); - } } return (device); } @@ -4564,86 +4525,6 @@ return (device); } -void -xpt_devise_transport(struct cam_path *path) -{ - struct ccb_pathinq cpi; - struct ccb_trans_settings cts; - struct scsi_inquiry_data *inq_buf; - - /* Get transport information from the SIM */ - xpt_setup_ccb(&cpi.ccb_h, path, /*priority*/1); - cpi.ccb_h.func_code = XPT_PATH_INQ; - xpt_action((union ccb *)&cpi); - - inq_buf = NULL; - if ((path->device->flags & CAM_DEV_INQUIRY_DATA_VALID) != 0) - inq_buf = &path->device->inq_data; - path->device->protocol = PROTO_SCSI; - path->device->protocol_version = - inq_buf != NULL ? SID_ANSI_REV(inq_buf) : cpi.protocol_version; - path->device->transport = cpi.transport; - path->device->transport_version = cpi.transport_version; - - /* - * Any device not using SPI3 features should - * be considered SPI2 or lower. - */ - if (inq_buf != NULL) { - if (path->device->transport == XPORT_SPI - && (inq_buf->spi3data & SID_SPI_MASK) == 0 - && path->device->transport_version > 2) - path->device->transport_version = 2; - } else { - struct cam_ed* otherdev; - - for (otherdev = TAILQ_FIRST(&path->target->ed_entries); - otherdev != NULL; - otherdev = TAILQ_NEXT(otherdev, links)) { - if (otherdev != path->device) - break; - } - - if (otherdev != NULL) { - /* - * Initially assume the same versioning as - * prior luns for this target. - */ - path->device->protocol_version = - otherdev->protocol_version; - path->device->transport_version = - otherdev->transport_version; - } else { - /* Until we know better, opt for safty */ - path->device->protocol_version = 2; - if (path->device->transport == XPORT_SPI) - path->device->transport_version = 2; - else - path->device->transport_version = 0; - } - } - - /* - * XXX - * For a device compliant with SPC-2 we should be able - * to determine the transport version supported by - * scrutinizing the version descriptors in the - * inquiry buffer. - */ - - /* Tell the controller what we think */ - xpt_setup_ccb(&cts.ccb_h, path, /*priority*/1); - cts.ccb_h.func_code = XPT_SET_TRAN_SETTINGS; - cts.type = CTS_TYPE_CURRENT_SETTINGS; - cts.transport = path->device->transport; - cts.transport_version = path->device->transport_version; - cts.protocol = path->device->protocol; - cts.protocol_version = path->device->protocol_version; - cts.proto_specific.valid = 0; - cts.xport_specific.valid = 0; - xpt_action((union ccb *)&cts); -} - static void xpt_set_transfer_settings(struct ccb_trans_settings *cts, struct cam_ed *device, int async_update) @@ -4734,7 +4615,7 @@ if ((cpi.hba_inquiry & PI_TAG_ABLE) == 0 || (INQ_DATA_TQ_ENABLED(inq_data)) == 0 || (device->queue_flags & SCP_QUEUE_DQUE) != 0 - || (device->quirk->mintags == 0)) { + || (device->mintags == 0)) { /* * Can't tag on hardware that doesn't support tags, * doesn't have it enabled, or has broken tag support. @@ -4980,7 +4861,7 @@ if (device->tag_saved_openings != 0) newopenings = device->tag_saved_openings; else - newopenings = min(device->quirk->maxtags, + newopenings = min(device->maxtags, sim->max_tagged_dev_openings); xpt_dev_ccbq_resize(path, newopenings); xpt_setup_ccb(&crs.ccb_h, path, /*priority*/1); ==== //depot/projects/scottl-camlock/src/sys/cam/cam_xpt.h#14 (text+ko) ==== @@ -94,8 +94,9 @@ struct periph_list periphs; /* All attached devices */ u_int generation; /* Generation number */ struct cam_periph *owner; /* Peripheral driver's ownership tag */ - struct xpt_quirk_entry *quirk; /* Oddities about this device */ - /* Storage for the inquiry data */ + void *quirk; /* Oddities about this device */ + u_int maxtags; + u_int mintags; cam_proto protocol; u_int protocol_version; cam_xport transport; @@ -169,6 +170,10 @@ struct cam_ed *device; }; +typedef struct cam_ed * (*xpt_alloc_device_func)(struct cam_eb *bus, + struct cam_et *target, + lun_id_t lun_id); + #if defined(CAM_DEBUG_FLAGS) && !defined(CAMDEBUG) #error "You must have options CAMDEBUG to use options CAM_DEBUG_FLAGS" #endif @@ -194,7 +199,9 @@ MALLOC_DECLARE(M_CAMXPT); void xpt_action(union ccb *new_ccb); -void xpt_devise_transport(struct cam_path *path); +static struct cam_ed* xpt_alloc_device(struct cam_eb *bus, + struct cam_et *target, + lun_id_t lun_id); void xpt_setup_ccb(struct ccb_hdr *ccb_h, struct cam_path *path, u_int32_t priority); ==== //depot/projects/scottl-camlock/src/sys/cam/scsi/scsi_xpt.c#8 (text+ko) ==== @@ -68,7 +68,7 @@ #include <machine/stdarg.h> /* for xpt_print below */ #include "opt_cam.h" -struct xpt_quirk_entry { +struct scsi_quirk_entry { struct scsi_inquiry_pattern inq_pat; u_int8_t quirks; #define CAM_QUIRK_NOLUNS 0x01 @@ -175,7 +175,7 @@ static const char seagate[] = "SEAGATE"; static const char microp[] = "MICROP"; -static struct xpt_quirk_entry xpt_quirk_table[] = +static struct scsi_quirk_entry scsi_quirk_table[] = { { /* Reports QUEUE FULL for temporary resource shortages */ @@ -518,8 +518,8 @@ }, }; -static const int xpt_quirk_table_size = - sizeof(xpt_quirk_table) / sizeof(*xpt_quirk_table); +static const int scsi_quirk_table_size = + sizeof(scsi_quirk_table) / sizeof(*scsi_quirk_table); static cam_status proberegister(struct cam_periph *periph, void *arg); @@ -536,6 +536,10 @@ struct cam_path *path, cam_flags flags, union ccb *ccb); static void xptscandone(struct cam_periph *periph, union ccb *done_ccb); +static struct cam_ed * + scsi_alloc_device(struct cam_eb *bus, struct cam_et *target, + lun_id_t lun_id); +static void scsi_devise_transport(struct cam_path *path); static void probe_periph_init() @@ -1395,17 +1399,21 @@ static void xpt_find_quirk(struct cam_ed *device) { + struct scsi_quirk_entry *quirk; caddr_t match; match = cam_quirkmatch((caddr_t)&device->inq_data, - (caddr_t)xpt_quirk_table, - sizeof(xpt_quirk_table)/sizeof(*xpt_quirk_table), - sizeof(*xpt_quirk_table), scsi_inquiry_match); + (caddr_t)scsi_quirk_table, + sizeof(scsi_quirk_table)/sizeof(*scsi__quirk_table), + sizeof(*scsi_quirk_table), scsi_inquiry_match); if (match == NULL) panic("xpt_find_quirk: device didn't match wildcard entry!!"); - device->quirk = (struct xpt_quirk_entry *)match; + quirk = (strut scsi_quirk_entry *)match; + device->quirk = quirk; + device->mintags = quirk->mintags; + device->maxtags = quirk->maxtags; } static int @@ -1796,3 +1804,137 @@ free(done_ccb, M_CAMXPT); } +static struct cam_ed * +scsi_alloc_device(struct cam_eb *bus, struct cam_et *target, lun_id_t lun_id) +{ + struct cam_path path; + struct scsi_quirk_entry *quirk; + struct cam_ed *device; + struct cam_ed *cur_device; + + device = xpt_alloc_device(bus, target, lun_id); + if (device == NULL) + return (NULL); + + /* + * Take the default quirk entry until we have inquiry + * data and can determine a better quirk to use. + */ + quirk = &scsi_quirk_table[scsi_quirk_table_size - 1]; + device->quirk = (void *)quirk; + device->mintags = quirk->mintags; + device->maxtags = quirk->maxtags; + bzero(&device->inq_data, sizeof(device->inq_data)); + device->inq_flags = 0; + device->queue_flags = 0; + device->serial_num = NULL; + device->serial_num_len = 0; + + /* + * XXX should be limited by number of CCBs this bus can + * do. + */ + bus->sim->max_ccbs += device->ccbq.devq_openings; + /* Insertion sort into our target's device list */ + cur_device = TAILQ_FIRST(&target->ed_entries); + while (cur_device != NULL && cur_device->lun_id < lun_id) + cur_device = TAILQ_NEXT(cur_device, links); + if (cur_device != NULL) { + TAILQ_INSERT_BEFORE(cur_device, device, links); + } else { + TAILQ_INSERT_TAIL(&target->ed_entries, device, links); + } + target->generation++; + if (lun_id != CAM_LUN_WILDCARD) { + xpt_compile_path(&path, + NULL, + bus->path_id, + target->target_id, + lun_id); + scsi_devise_transport(&path); + xpt_release_path(&path); + } + + return (device); +} + +static void +scsi_devise_transport(struct cam_path *path) +{ + struct ccb_pathinq cpi; + struct ccb_trans_settings cts; + struct scsi_inquiry_data *inq_buf; + + /* Get transport information from the SIM */ + xpt_setup_ccb(&cpi.ccb_h, path, /*priority*/1); + cpi.ccb_h.func_code = XPT_PATH_INQ; + xpt_action((union ccb *)&cpi); + + inq_buf = NULL; + if ((path->device->flags & CAM_DEV_INQUIRY_DATA_VALID) != 0) + inq_buf = &path->device->inq_data; + path->device->protocol = PROTO_SCSI; + path->device->protocol_version = + inq_buf != NULL ? SID_ANSI_REV(inq_buf) : cpi.protocol_version; + path->device->transport = cpi.transport; + path->device->transport_version = cpi.transport_version; + + /* + * Any device not using SPI3 features should + * be considered SPI2 or lower. + */ + if (inq_buf != NULL) { + if (path->device->transport == XPORT_SPI + && (inq_buf->spi3data & SID_SPI_MASK) == 0 + && path->device->transport_version > 2) + path->device->transport_version = 2; + } else { + struct cam_ed* otherdev; + + for (otherdev = TAILQ_FIRST(&path->target->ed_entries); + otherdev != NULL; + otherdev = TAILQ_NEXT(otherdev, links)) { + if (otherdev != path->device) + break; + } + + if (otherdev != NULL) { + /* + * Initially assume the same versioning as + * prior luns for this target. + */ + path->device->protocol_version = + otherdev->protocol_version; + path->device->transport_version = + otherdev->transport_version; + } else { + /* Until we know better, opt for safty */ + path->device->protocol_version = 2; + if (path->device->transport == XPORT_SPI) + path->device->transport_version = 2; + else + path->device->transport_version = 0; + } + } + + /* + * XXX + * For a device compliant with SPC-2 we should be able + * to determine the transport version supported by + * scrutinizing the version descriptors in the + * inquiry buffer. + */ + + /* Tell the controller what we think */ + xpt_setup_ccb(&cts.ccb_h, path, /*priority*/1); + cts.ccb_h.func_code = XPT_SET_TRAN_SETTINGS; + cts.type = CTS_TYPE_CURRENT_SETTINGS; + cts.transport = path->device->transport; + cts.transport_version = path->device->transport_version; + cts.protocol = path->device->protocol; + cts.protocol_version = path->device->protocol_version; + cts.proto_specific.valid = 0; + cts.xport_specific.valid = 0; + xpt_action((union ccb *)&cts); +} +
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200904080812.n388C3Ks004914>
