From nobody Thu May 11 04:28:11 2023 X-Original-To: dev-commits-src-all@mlmmj.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mlmmj.nyi.freebsd.org (Postfix) with ESMTP id 4QGzQz29pQz49dXd; Thu, 11 May 2023 04:28:11 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "R3" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id 4QGzQz1yhwz4Clb; Thu, 11 May 2023 04:28:11 +0000 (UTC) (envelope-from git@FreeBSD.org) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1683779291; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=4Nu07GuLTa7R52fpelYE2dZ4i3Y2vXJVOZWmZ8hiv1I=; b=rudzmD57B9ZZCmfcEnngyRXgRfVd7Tstmbq4w3JPKcj9U5VObjtD4i9Lclq73I/pVAaLoP rbmbUcBkfkQANF/J0hMAFYhw2YlvwlERNYf9tqAUEFC7cahNNjDkDEyFvk40cqM1j9jClJ tRgjX1h8hN0sc6ZkuJBWUIWH+Pz6lEcT5ZvMRpVy4yEXUSvkzRXlqBfhCYwfYVz4SRmLRk Ksaj8eLsl9XL+reRoUoRyObSrZnYMD1O2YALpmtQHcxX5LgHqETlmo0nKJ50ZRoP4GQAq+ SYYkGwhQVSHUMVVBkQrwAoXcdgY903tVYj4HaoS+TgRQiN6eYzs2zVoqcuBeUw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1683779291; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=4Nu07GuLTa7R52fpelYE2dZ4i3Y2vXJVOZWmZ8hiv1I=; b=hCrEd1lxoVCM5D0/zCJfLAAJJFT77EW4m6Sy4zvX1iSJbOjtnRm9EhEXorjB3AYgtrlQR+ 9w1jHWPdqldJptDUIqqvQ4zFJOOGa18ZmUChHCjb5N7AdaLTkqVZXeYDZHMOM2nPSRNXge HO32kbKCezlSoE+G+B1Af2XkJVmR7rTPmDKaOJU15QHxR5lAPyEPJkb++9j8WUPHWg+K7Q ndRDv5s8hX5rWkKLAIAUpJ+4HdgqJES3SgvKANULrU+glAqMNQrlmqGzWsAdSCzwJUzQ3W PwWC2ImrBsi+sWWvykDvY0LfMWJeHFQjll402SAzdkuhJ5A8hZIsP/+7Rce7Bg== ARC-Authentication-Results: i=1; mx1.freebsd.org; none ARC-Seal: i=1; s=dkim; d=freebsd.org; t=1683779291; a=rsa-sha256; cv=none; b=DckH2WIHoQu3U11ydilDxOaqXhJ0dsH4TEfr1V/uSC35imVebUM9Y+5AHsHB5IrSJDzsvQ lHuQQKQ2rr0n/jgUZSgLq9Zol+WgE5B4SwuUcfb2CMhmVsBp1cdmAr4gPKIsn6LgtgZwIN xhDrlHuOIgDHCJvCiOrxZYKR55awtM0p/vZ1NeEiQGdv/LoXZhckgUROU5g0RzVblG3rgR iLKeeNoKZcnEP5MgoppIflpXycrd22grzQgUW14iqwHvsTK/s8WUvneznuAL3Fg11kn0LI IJe2awvr1LGGjnLJG/eJJ4vV8NnfPLXMYgFSHXBhDpnJ8IDM8boLfwS9uDkyMQ== Received: from gitrepo.freebsd.org (gitrepo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:5]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 4QGzQz10qBzf5r; Thu, 11 May 2023 04:28:11 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from gitrepo.freebsd.org ([127.0.1.44]) by gitrepo.freebsd.org (8.16.1/8.16.1) with ESMTP id 34B4SBoP069778; Thu, 11 May 2023 04:28:11 GMT (envelope-from git@gitrepo.freebsd.org) Received: (from git@localhost) by gitrepo.freebsd.org (8.16.1/8.16.1/Submit) id 34B4SBRD069777; Thu, 11 May 2023 04:28:11 GMT (envelope-from git) Date: Thu, 11 May 2023 04:28:11 GMT Message-Id: <202305110428.34B4SBRD069777@gitrepo.freebsd.org> To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-main@FreeBSD.org From: Warner Losh Subject: git: 062a7b918fac - main - twe: Remove driver List-Id: Commit messages for all branches of the src repository List-Archive: https://lists.freebsd.org/archives/dev-commits-src-all List-Help: List-Post: List-Subscribe: List-Unsubscribe: Sender: owner-dev-commits-src-all@freebsd.org X-BeenThere: dev-commits-src-all@freebsd.org MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit X-Git-Committer: imp X-Git-Repository: src X-Git-Refname: refs/heads/main X-Git-Reftype: branch X-Git-Commit: 062a7b918fac638e0cce0d8c087d7f2190c59b1e Auto-Submitted: auto-generated X-ThisMailContainsUnwantedMimeParts: N The branch main has been updated by imp: URL: https://cgit.FreeBSD.org/src/commit/?id=062a7b918fac638e0cce0d8c087d7f2190c59b1e commit 062a7b918fac638e0cce0d8c087d7f2190c59b1e Author: Warner Losh AuthorDate: 2023-05-11 04:24:12 +0000 Commit: Warner Losh CommitDate: 2023-05-11 04:24:12 +0000 twe: Remove driver Sponsored by: Netflix --- sys/amd64/conf/GENERIC | 1 - sys/conf/NOTES | 5 - sys/conf/files | 2 - sys/dev/twe/twe.c | 1973 --------------------------------------------- sys/dev/twe/twe_compat.h | 127 --- sys/dev/twe/twe_freebsd.c | 1170 --------------------------- sys/dev/twe/twe_tables.h | 169 ---- sys/dev/twe/tweio.h | 106 --- sys/dev/twe/twereg.h | 496 ------------ sys/dev/twe/twevar.h | 274 ------- sys/modules/Makefile | 1 - sys/modules/twe/Makefile | 30 - 12 files changed, 4354 deletions(-) diff --git a/sys/amd64/conf/GENERIC b/sys/amd64/conf/GENERIC index f3497ef91f63..8f2e5e9fccb4 100644 --- a/sys/amd64/conf/GENERIC +++ b/sys/amd64/conf/GENERIC @@ -195,7 +195,6 @@ device mlx # Mylex DAC960 family device mrsas # LSI/Avago MegaRAID SAS/SATA, 6Gb/s and 12Gb/s #XXX pointer/int warnings #device pst # Promise Supertrak SX6000 -device twe # 3ware ATA RAID # NVM Express (NVMe) support device nvme # base NVMe driver diff --git a/sys/conf/NOTES b/sys/conf/NOTES index a6c3c42fc00e..8725d11a5434 100644 --- a/sys/conf/NOTES +++ b/sys/conf/NOTES @@ -1646,11 +1646,6 @@ device mfip # LSI MegaRAID SAS passthrough, requires CAM options MFI_DEBUG device mrsas # LSI/Avago MegaRAID SAS/SATA, 6Gb/s and 12Gb/s -# -# 3ware ATA RAID -# -device twe # 3ware ATA RAID - # # Serial ATA host controllers: # diff --git a/sys/conf/files b/sys/conf/files index 8c3d80c48b01..c0728504da5a 100644 --- a/sys/conf/files +++ b/sys/conf/files @@ -3171,8 +3171,6 @@ dev/syscons/warp/warp_saver.c optional warp_saver dev/tcp_log/tcp_log_dev.c optional tcp_blackbox inet | tcp_blackbox inet6 dev/tdfx/tdfx_pci.c optional tdfx pci dev/ti/if_ti.c optional ti pci -dev/twe/twe.c optional twe -dev/twe/twe_freebsd.c optional twe dev/tws/tws.c optional tws dev/tws/tws_cam.c optional tws dev/tws/tws_hdm.c optional tws diff --git a/sys/dev/twe/twe.c b/sys/dev/twe/twe.c deleted file mode 100644 index 6d05ac7c2b95..000000000000 --- a/sys/dev/twe/twe.c +++ /dev/null @@ -1,1973 +0,0 @@ -/*- - * SPDX-License-Identifier: BSD-2-Clause-FreeBSD - * - * Copyright (c) 2000 Michael Smith - * Copyright (c) 2003 Paul Saab - * Copyright (c) 2003 Vinod Kashyap - * Copyright (c) 2000 BSDi - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $FreeBSD$ - */ - -/* - * Driver for the 3ware Escalade family of IDE RAID controllers. - */ - -#include -#include -#include -#include -#define TWE_DEFINE_TABLES -#include - -/* - * Command submission. - */ -static int twe_get_param_1(struct twe_softc *sc, int table_id, int param_id, u_int8_t *result); -static int twe_get_param_2(struct twe_softc *sc, int table_id, int param_id, u_int16_t *result); -static int twe_get_param_4(struct twe_softc *sc, int table_id, int param_id, u_int32_t *result); -static void *twe_get_param(struct twe_softc *sc, int table_id, int parameter_id, size_t size, - void (* func)(struct twe_request *tr)); -#ifdef TWE_SHUTDOWN_NOTIFICATION -static int twe_set_param_1(struct twe_softc *sc, int table_id, int param_id, u_int8_t value); -#endif -#if 0 -static int twe_set_param_2(struct twe_softc *sc, int table_id, int param_id, u_int16_t value); -static int twe_set_param_4(struct twe_softc *sc, int table_id, int param_id, u_int32_t value); -#endif -static int twe_set_param(struct twe_softc *sc, int table_id, int param_id, int param_size, - void *data); -static int twe_init_connection(struct twe_softc *sc, int mode); -static int twe_wait_request(struct twe_request *tr); -static int twe_immediate_request(struct twe_request *tr, int usetmp); -static void twe_completeio(struct twe_request *tr); -static void twe_reset(struct twe_softc *sc); -static int twe_add_unit(struct twe_softc *sc, int unit); -static int twe_del_unit(struct twe_softc *sc, int unit); - -/* - * Command I/O to controller. - */ -static void twe_done(struct twe_softc *sc, int startio); -static void twe_complete(struct twe_softc *sc); -static int twe_wait_status(struct twe_softc *sc, u_int32_t status, int timeout); -static int twe_drain_response_queue(struct twe_softc *sc); -static int twe_check_bits(struct twe_softc *sc, u_int32_t status_reg); -static int twe_soft_reset(struct twe_softc *sc); - -/* - * Interrupt handling. - */ -static void twe_host_intr(struct twe_softc *sc); -static void twe_attention_intr(struct twe_softc *sc); -static void twe_command_intr(struct twe_softc *sc); - -/* - * Asynchronous event handling. - */ -static int twe_fetch_aen(struct twe_softc *sc); -static void twe_handle_aen(struct twe_request *tr); -static void twe_enqueue_aen(struct twe_softc *sc, u_int16_t aen); -static u_int16_t twe_dequeue_aen(struct twe_softc *sc); -static int twe_drain_aen_queue(struct twe_softc *sc); -static int twe_find_aen(struct twe_softc *sc, u_int16_t aen); - -/* - * Command buffer management. - */ -static int twe_get_request(struct twe_softc *sc, struct twe_request **tr); -static void twe_release_request(struct twe_request *tr); - -/* - * Debugging. - */ -static char *twe_format_aen(struct twe_softc *sc, u_int16_t aen); -static int twe_report_request(struct twe_request *tr); -static void twe_panic(struct twe_softc *sc, char *reason); - -/******************************************************************************** - ******************************************************************************** - Public Interfaces - ******************************************************************************** - ********************************************************************************/ - -/******************************************************************************** - * Initialise the controller, set up driver data structures. - */ -int -twe_setup(struct twe_softc *sc) -{ - struct twe_request *tr; - TWE_Command *cmd; - u_int32_t status_reg; - int i; - - debug_called(4); - - gone_in(14, "Please migrate to newer hardware"); - - /* - * Initialise request queues. - */ - twe_initq_free(sc); - twe_initq_bio(sc); - twe_initq_ready(sc); - twe_initq_busy(sc); - twe_initq_complete(sc); - sc->twe_wait_aen = -1; - - /* - * Allocate request structures up front. - */ - for (i = 0; i < TWE_Q_LENGTH; i++) { - if ((tr = twe_allocate_request(sc, i)) == NULL) - return(ENOMEM); - /* - * Set global defaults that won't change. - */ - cmd = TWE_FIND_COMMAND(tr); - cmd->generic.host_id = sc->twe_host_id; /* controller-assigned host ID */ - cmd->generic.request_id = i; /* our index number */ - sc->twe_lookup[i] = tr; - - /* - * Put command onto the freelist. - */ - TWE_IO_LOCK(sc); - twe_release_request(tr); - TWE_IO_UNLOCK(sc); - } - TWE_IO_LOCK(sc); - - /* - * Check status register for errors, clear them. - */ - status_reg = TWE_STATUS(sc); - twe_check_bits(sc, status_reg); - - /* - * Wait for the controller to come ready. - */ - if (twe_wait_status(sc, TWE_STATUS_MICROCONTROLLER_READY, 60)) { - TWE_IO_UNLOCK(sc); - twe_printf(sc, "microcontroller not ready\n"); - return(ENXIO); - } - - /* - * Disable interrupts from the card. - */ - twe_disable_interrupts(sc); - - /* - * Soft reset the controller, look for the AEN acknowledging the reset, - * check for errors, drain the response queue. - */ - for (i = 0; i < TWE_MAX_RESET_TRIES; i++) { - if (i > 0) - twe_printf(sc, "reset %d failed, trying again\n", i); - - if (!twe_soft_reset(sc)) - break; /* reset process complete */ - } - TWE_IO_UNLOCK(sc); - /* did we give up? */ - if (i >= TWE_MAX_RESET_TRIES) { - twe_printf(sc, "can't initialise controller, giving up\n"); - return(ENXIO); - } - - return(0); -} - -static int -twe_add_unit(struct twe_softc *sc, int unit) -{ - struct twe_drive *dr; - int table, error = 0; - u_int16_t dsize; - TWE_Param *drives = NULL, *param = NULL; - TWE_Array_Descriptor *ud; - - TWE_CONFIG_ASSERT_LOCKED(sc); - if (unit < 0 || unit > TWE_MAX_UNITS) - return (EINVAL); - - /* - * The controller is in a safe state, so try to find drives attached to it. - */ - TWE_IO_LOCK(sc); - if ((drives = twe_get_param(sc, TWE_PARAM_UNITSUMMARY, TWE_PARAM_UNITSUMMARY_Status, - TWE_MAX_UNITS, NULL)) == NULL) { - TWE_IO_UNLOCK(sc); - twe_printf(sc, "can't detect attached units\n"); - return (EIO); - } - - dr = &sc->twe_drive[unit]; - /* check that the drive is online */ - if (!(drives->data[unit] & TWE_PARAM_UNITSTATUS_Online)) { - TWE_IO_UNLOCK(sc); - error = ENXIO; - goto out; - } - - table = TWE_PARAM_UNITINFO + unit; - - if (twe_get_param_4(sc, table, TWE_PARAM_UNITINFO_Capacity, &dr->td_size)) { - TWE_IO_UNLOCK(sc); - twe_printf(sc, "error fetching capacity for unit %d\n", unit); - error = EIO; - goto out; - } - if (twe_get_param_1(sc, table, TWE_PARAM_UNITINFO_Status, &dr->td_state)) { - TWE_IO_UNLOCK(sc); - twe_printf(sc, "error fetching state for unit %d\n", unit); - error = EIO; - goto out; - } - if (twe_get_param_2(sc, table, TWE_PARAM_UNITINFO_DescriptorSize, &dsize)) { - TWE_IO_UNLOCK(sc); - twe_printf(sc, "error fetching descriptor size for unit %d\n", unit); - error = EIO; - goto out; - } - if ((param = twe_get_param(sc, table, TWE_PARAM_UNITINFO_Descriptor, dsize - 3, NULL)) == NULL) { - TWE_IO_UNLOCK(sc); - twe_printf(sc, "error fetching descriptor for unit %d\n", unit); - error = EIO; - goto out; - } - ud = (TWE_Array_Descriptor *)param->data; - dr->td_type = ud->configuration; - dr->td_stripe = ud->stripe_size; - - /* build synthetic geometry as per controller internal rules */ - if (dr->td_size > 0x200000) { - dr->td_heads = 255; - dr->td_sectors = 63; - } else { - dr->td_heads = 64; - dr->td_sectors = 32; - } - dr->td_cylinders = dr->td_size / (dr->td_heads * dr->td_sectors); - dr->td_twe_unit = unit; - TWE_IO_UNLOCK(sc); - - error = twe_attach_drive(sc, dr); - -out: - if (param != NULL) - free(param, M_DEVBUF); - if (drives != NULL) - free(drives, M_DEVBUF); - return (error); -} - -static int -twe_del_unit(struct twe_softc *sc, int unit) -{ - int error; - - TWE_CONFIG_ASSERT_LOCKED(sc); - if (unit < 0 || unit >= TWE_MAX_UNITS) - return (ENXIO); - - if (sc->twe_drive[unit].td_disk == NULL) - return (ENXIO); - - error = twe_detach_drive(sc, unit); - return (error); -} - -/******************************************************************************** - * Locate disk devices and attach children to them. - */ -void -twe_init(struct twe_softc *sc) -{ - int i; - - /* - * Scan for drives - */ - TWE_CONFIG_LOCK(sc); - for (i = 0; i < TWE_MAX_UNITS; i++) - twe_add_unit(sc, i); - TWE_CONFIG_UNLOCK(sc); - - /* - * Initialise connection with controller. - */ - TWE_IO_LOCK(sc); - twe_init_connection(sc, TWE_INIT_MESSAGE_CREDITS); - -#ifdef TWE_SHUTDOWN_NOTIFICATION - /* - * Tell the controller we support shutdown notification. - */ - twe_set_param_1(sc, TWE_PARAM_FEATURES, TWE_PARAM_FEATURES_DriverShutdown, 1); -#endif - - /* - * Mark controller up and ready to run. - */ - sc->twe_state &= ~TWE_STATE_SHUTDOWN; - - /* - * Finally enable interrupts. - */ - twe_enable_interrupts(sc); - TWE_IO_UNLOCK(sc); -} - -/******************************************************************************** - * Stop the controller - */ -void -twe_deinit(struct twe_softc *sc) -{ - /* - * Mark the controller as shutting down, and disable any further interrupts. - */ - TWE_IO_ASSERT_LOCKED(sc); - sc->twe_state |= TWE_STATE_SHUTDOWN; - twe_disable_interrupts(sc); - -#ifdef TWE_SHUTDOWN_NOTIFICATION - /* - * Disconnect from the controller - */ - twe_init_connection(sc, TWE_SHUTDOWN_MESSAGE_CREDITS); -#endif -} - -/******************************************************************************* - * Take an interrupt, or be poked by other code to look for interrupt-worthy - * status. - */ -void -twe_intr(struct twe_softc *sc) -{ - u_int32_t status_reg; - - debug_called(4); - - /* - * Collect current interrupt status. - */ - status_reg = TWE_STATUS(sc); - twe_check_bits(sc, status_reg); - - /* - * Dispatch based on interrupt status - */ - if (status_reg & TWE_STATUS_HOST_INTERRUPT) - twe_host_intr(sc); - if (status_reg & TWE_STATUS_ATTENTION_INTERRUPT) - twe_attention_intr(sc); - if (status_reg & TWE_STATUS_COMMAND_INTERRUPT) - twe_command_intr(sc); - if (status_reg & TWE_STATUS_RESPONSE_INTERRUPT) - twe_done(sc, 1); -}; - -/******************************************************************************** - * Pull as much work off the softc's work queue as possible and give it to the - * controller. - */ -void -twe_startio(struct twe_softc *sc) -{ - struct twe_request *tr; - TWE_Command *cmd; - struct bio *bp; - int error; - - debug_called(4); - - TWE_IO_ASSERT_LOCKED(sc); - if (sc->twe_state & (TWE_STATE_CTLR_BUSY | TWE_STATE_FRZN)) - return; - - /* spin until something prevents us from doing any work */ - for (;;) { - /* try to get a command that's already ready to go */ - tr = twe_dequeue_ready(sc); - - /* build a command from an outstanding bio */ - if (tr == NULL) { - - /* get a command to handle the bio with */ - if (twe_get_request(sc, &tr)) - break; - - /* see if there's work to be done */ - if ((bp = twe_dequeue_bio(sc)) == NULL) { - twe_release_request(tr); - break; - } - - /* connect the bio to the command */ - tr->tr_complete = twe_completeio; - tr->tr_private = bp; - tr->tr_data = bp->bio_data; - tr->tr_length = bp->bio_bcount; - cmd = TWE_FIND_COMMAND(tr); - if (bp->bio_cmd == BIO_READ) { - tr->tr_flags |= TWE_CMD_DATAIN; - cmd->io.opcode = TWE_OP_READ; - } else if (bp->bio_cmd == BIO_WRITE) { - tr->tr_flags |= TWE_CMD_DATAOUT; - cmd->io.opcode = TWE_OP_WRITE; - } else { - twe_release_request(tr); - biofinish(bp, NULL, EOPNOTSUPP); - break; - } - - /* build a suitable I/O command (assumes 512-byte rounded transfers) */ - cmd->io.size = 3; - cmd->io.unit = *(int *)(bp->bio_driver1); - cmd->io.block_count = (tr->tr_length + TWE_BLOCK_SIZE - 1) / TWE_BLOCK_SIZE; - cmd->io.lba = bp->bio_pblkno; - } - - /* did we find something to do? */ - if (tr == NULL) - break; - - /* try to map and submit the command to controller */ - error = twe_map_request(tr); - - if (error != 0) { - if (error == EBUSY) - break; - tr->tr_status = TWE_CMD_ERROR; - if (tr->tr_private != NULL) { - bp = (struct bio *)(tr->tr_private); - bp->bio_error = error; - bp->bio_flags |= BIO_ERROR; - tr->tr_private = NULL; - twed_intr(bp); - twe_release_request(tr); - } else if (tr->tr_flags & TWE_CMD_SLEEPER) - wakeup_one(tr); /* wakeup the sleeping owner */ - } - } -} - -/******************************************************************************** - * Write blocks from memory to disk, for system crash dumps. - */ -int -twe_dump_blocks(struct twe_softc *sc, int unit, u_int32_t lba, void *data, int nblks) -{ - struct twe_request *tr; - TWE_Command *cmd; - int error; - - if (twe_get_request(sc, &tr)) - return(ENOMEM); - - tr->tr_data = data; - tr->tr_status = TWE_CMD_SETUP; - tr->tr_length = nblks * TWE_BLOCK_SIZE; - tr->tr_flags = TWE_CMD_DATAOUT; - - cmd = TWE_FIND_COMMAND(tr); - cmd->io.opcode = TWE_OP_WRITE; - cmd->io.size = 3; - cmd->io.unit = unit; - cmd->io.block_count = nblks; - cmd->io.lba = lba; - - error = twe_immediate_request(tr, 0); - if (error == 0) - if (twe_report_request(tr)) - error = EIO; - twe_release_request(tr); - return(error); -} - -/******************************************************************************** - * Handle controller-specific control operations. - */ -int -twe_ioctl(struct twe_softc *sc, u_long ioctlcmd, void *addr) -{ - struct twe_usercommand *tu = (struct twe_usercommand *)addr; - struct twe_paramcommand *tp = (struct twe_paramcommand *)addr; - struct twe_drivecommand *td = (struct twe_drivecommand *)addr; - union twe_statrequest *ts = (union twe_statrequest *)addr; - TWE_Param *param; - TWE_Command *cmd; - void *data; - u_int16_t *aen_code = (u_int16_t *)addr; - struct twe_request *tr; - u_int8_t srid; - int error; - size_t tr_length; - - error = 0; - switch(ioctlcmd) { - /* handle a command from userspace */ - case TWEIO_COMMAND: - /* - * if there's a data buffer, allocate and copy it in. - * Must be in multiplied of 512 bytes. - */ - tr_length = roundup2(tu->tu_size, 512); - if (tr_length > 0) { - data = malloc(tr_length, M_DEVBUF, M_WAITOK); - error = copyin(tu->tu_data, data, tu->tu_size); - if (error) { - free(data, M_DEVBUF); - break; - } - } else - data = NULL; - - /* get a request */ - TWE_IO_LOCK(sc); - while (twe_get_request(sc, &tr)) - mtx_sleep(sc, &sc->twe_io_lock, PPAUSE, "twioctl", hz); - - /* - * Save the command's request ID, copy the user-supplied command in, - * restore the request ID. - */ - cmd = TWE_FIND_COMMAND(tr); - srid = cmd->generic.request_id; - bcopy(&tu->tu_command, cmd, sizeof(TWE_Command)); - cmd->generic.request_id = srid; - - tr->tr_length = tr_length; - tr->tr_data = data; - if (tr->tr_length > 0) { - tr->tr_flags |= TWE_CMD_DATAIN | TWE_CMD_DATAOUT; - } - - /* run the command */ - error = twe_wait_request(tr); - TWE_IO_UNLOCK(sc); - if (error) - goto cmd_done; - - /* copy the command out again */ - bcopy(cmd, &tu->tu_command, sizeof(TWE_Command)); - - /* if there was a data buffer, copy it out */ - if (tr->tr_length > 0) - error = copyout(tr->tr_data, tu->tu_data, tu->tu_size); - - cmd_done: - /* free resources */ - if (tr->tr_data != NULL) - free(tr->tr_data, M_DEVBUF); - TWE_IO_LOCK(sc); - twe_release_request(tr); - TWE_IO_UNLOCK(sc); - - break; - - /* fetch statistics counter */ - case TWEIO_STATS: - switch (ts->ts_item) { -#ifdef TWE_PERFORMANCE_MONITOR - case TWEQ_FREE: - case TWEQ_BIO: - case TWEQ_READY: - case TWEQ_BUSY: - case TWEQ_COMPLETE: - TWE_IO_LOCK(sc); - bcopy(&sc->twe_qstat[ts->ts_item], &ts->ts_qstat, sizeof(struct twe_qstat)); - TWE_IO_UNLOCK(sc); - break; -#endif - default: - error = ENOENT; - break; - } - break; - - /* poll for an AEN */ - case TWEIO_AEN_POLL: - TWE_IO_LOCK(sc); - *aen_code = twe_dequeue_aen(sc); - TWE_IO_UNLOCK(sc); - break; - - /* wait for another AEN to show up */ - case TWEIO_AEN_WAIT: - TWE_IO_LOCK(sc); - while ((*aen_code = twe_dequeue_aen(sc)) == TWE_AEN_QUEUE_EMPTY) { - error = mtx_sleep(&sc->twe_aen_queue, &sc->twe_io_lock, PRIBIO | PCATCH, - "tweaen", 0); - if (error == EINTR) - break; - } - TWE_IO_UNLOCK(sc); - break; - - case TWEIO_GET_PARAM: - TWE_IO_LOCK(sc); - param = twe_get_param(sc, tp->tp_table_id, tp->tp_param_id, tp->tp_size, NULL); - TWE_IO_UNLOCK(sc); - if (param == NULL) { - twe_printf(sc, "TWEIO_GET_PARAM failed for 0x%x/0x%x/%d\n", - tp->tp_table_id, tp->tp_param_id, tp->tp_size); - error = EINVAL; - } else { - if (param->parameter_size_bytes > tp->tp_size) { - twe_printf(sc, "TWEIO_GET_PARAM parameter too large (%d > %d)\n", - param->parameter_size_bytes, tp->tp_size); - error = EFAULT; - } else { - error = copyout(param->data, tp->tp_data, param->parameter_size_bytes); - } - free(param, M_DEVBUF); - } - break; - - case TWEIO_SET_PARAM: - data = malloc(tp->tp_size, M_DEVBUF, M_WAITOK); - error = copyin(tp->tp_data, data, tp->tp_size); - if (error == 0) { - TWE_IO_LOCK(sc); - error = twe_set_param(sc, tp->tp_table_id, tp->tp_param_id, tp->tp_size, data); - TWE_IO_UNLOCK(sc); - } - free(data, M_DEVBUF); - break; - - case TWEIO_RESET: - TWE_IO_LOCK(sc); - twe_reset(sc); - TWE_IO_UNLOCK(sc); - break; - - case TWEIO_ADD_UNIT: - TWE_CONFIG_LOCK(sc); - error = twe_add_unit(sc, td->td_unit); - TWE_CONFIG_UNLOCK(sc); - break; - - case TWEIO_DEL_UNIT: - TWE_CONFIG_LOCK(sc); - error = twe_del_unit(sc, td->td_unit); - TWE_CONFIG_UNLOCK(sc); - break; - - /* XXX implement ATA PASSTHROUGH */ - - /* nothing we understand */ - default: - error = ENOTTY; - } - - return(error); -} - -/******************************************************************************** - * Enable the useful interrupts from the controller. - */ -void -twe_enable_interrupts(struct twe_softc *sc) -{ - sc->twe_state |= TWE_STATE_INTEN; - TWE_CONTROL(sc, - TWE_CONTROL_CLEAR_ATTENTION_INTERRUPT | - TWE_CONTROL_UNMASK_RESPONSE_INTERRUPT | - TWE_CONTROL_ENABLE_INTERRUPTS); -} - -/******************************************************************************** - * Disable interrupts from the controller. - */ -void -twe_disable_interrupts(struct twe_softc *sc) -{ - TWE_CONTROL(sc, TWE_CONTROL_DISABLE_INTERRUPTS); - sc->twe_state &= ~TWE_STATE_INTEN; -} - -/******************************************************************************** - ******************************************************************************** - Command Submission - ******************************************************************************** - ********************************************************************************/ - -/******************************************************************************** - * Read integer parameter table entries. - */ -static int -twe_get_param_1(struct twe_softc *sc, int table_id, int param_id, u_int8_t *result) -{ - TWE_Param *param; - - if ((param = twe_get_param(sc, table_id, param_id, 1, NULL)) == NULL) - return(ENOENT); - *result = *(u_int8_t *)param->data; - free(param, M_DEVBUF); - return(0); -} - -static int -twe_get_param_2(struct twe_softc *sc, int table_id, int param_id, u_int16_t *result) -{ - TWE_Param *param; - - if ((param = twe_get_param(sc, table_id, param_id, 2, NULL)) == NULL) - return(ENOENT); - *result = *(u_int16_t *)param->data; - free(param, M_DEVBUF); - return(0); -} - -static int -twe_get_param_4(struct twe_softc *sc, int table_id, int param_id, u_int32_t *result) -{ - TWE_Param *param; - - if ((param = twe_get_param(sc, table_id, param_id, 4, NULL)) == NULL) - return(ENOENT); - *result = *(u_int32_t *)param->data; - free(param, M_DEVBUF); - return(0); -} - -/******************************************************************************** - * Perform a TWE_OP_GET_PARAM command. If a callback function is provided, it - * will be called with the command when it's completed. If no callback is - * provided, we will wait for the command to complete and then return just the data. - * The caller is responsible for freeing the data when done with it. - */ -static void * -twe_get_param(struct twe_softc *sc, int table_id, int param_id, size_t param_size, - void (* func)(struct twe_request *tr)) -{ - struct twe_request *tr; - TWE_Command *cmd; - TWE_Param *param; - int error; - - debug_called(4); - - TWE_IO_ASSERT_LOCKED(sc); - tr = NULL; - param = NULL; - - /* get a command */ - if (twe_get_request(sc, &tr)) - goto err; - - /* get a buffer */ - if ((param = (TWE_Param *)malloc(TWE_SECTOR_SIZE, M_DEVBUF, M_NOWAIT)) == NULL) - goto err; - tr->tr_data = param; - tr->tr_length = TWE_SECTOR_SIZE; - tr->tr_flags = TWE_CMD_DATAIN | TWE_CMD_DATAOUT; - - /* build the command for the controller */ - cmd = TWE_FIND_COMMAND(tr); - cmd->param.opcode = TWE_OP_GET_PARAM; - cmd->param.size = 2; - cmd->param.unit = 0; - cmd->param.param_count = 1; - - /* fill in the outbound parameter data */ - param->table_id = table_id; - param->parameter_id = param_id; - param->parameter_size_bytes = param_size; - - /* submit the command and either wait or let the callback handle it */ - if (func == NULL) { - /* XXX could use twe_wait_request here if interrupts were enabled? */ - error = twe_immediate_request(tr, 1 /* usetmp */); - if (error == 0) { - if (twe_report_request(tr)) - goto err; - } else { - goto err; - } - twe_release_request(tr); - return(param); - } else { - tr->tr_complete = func; - error = twe_map_request(tr); - if ((error == 0) || (error == EBUSY)) - return(func); - } - - /* something failed */ -err: - debug(1, "failed"); - if (tr != NULL) - twe_release_request(tr); - if (param != NULL) - free(param, M_DEVBUF); - return(NULL); -} - -/******************************************************************************** - * Set integer parameter table entries. - */ -#ifdef TWE_SHUTDOWN_NOTIFICATION -static int -twe_set_param_1(struct twe_softc *sc, int table_id, int param_id, u_int8_t value) -{ - return(twe_set_param(sc, table_id, param_id, sizeof(value), &value)); -} -#endif - -#if 0 -static int -twe_set_param_2(struct twe_softc *sc, int table_id, int param_id, u_int16_t value) -{ - return(twe_set_param(sc, table_id, param_id, sizeof(value), &value)); -} - -static int -twe_set_param_4(struct twe_softc *sc, int table_id, int param_id, u_int32_t value) -{ - return(twe_set_param(sc, table_id, param_id, sizeof(value), &value)); -} -#endif - -/******************************************************************************** - * Perform a TWE_OP_SET_PARAM command, returns nonzero on error. - */ -static int -twe_set_param(struct twe_softc *sc, int table_id, int param_id, int param_size, void *data) -{ - struct twe_request *tr; - TWE_Command *cmd; - TWE_Param *param; - int error; - - debug_called(4); - - TWE_IO_ASSERT_LOCKED(sc); - tr = NULL; - param = NULL; - error = ENOMEM; - - /* get a command */ - if (twe_get_request(sc, &tr)) - goto out; - - /* get a buffer */ - if ((param = (TWE_Param *)malloc(TWE_SECTOR_SIZE, M_DEVBUF, M_NOWAIT)) == NULL) - goto out; - tr->tr_data = param; - tr->tr_length = TWE_SECTOR_SIZE; - tr->tr_flags = TWE_CMD_DATAIN | TWE_CMD_DATAOUT; - - /* build the command for the controller */ - cmd = TWE_FIND_COMMAND(tr); - cmd->param.opcode = TWE_OP_SET_PARAM; - cmd->param.size = 2; - cmd->param.unit = 0; - cmd->param.param_count = 1; - - /* fill in the outbound parameter data */ - param->table_id = table_id; - param->parameter_id = param_id; - param->parameter_size_bytes = param_size; - bcopy(data, param->data, param_size); - - /* XXX could use twe_wait_request here if interrupts were enabled? */ - error = twe_immediate_request(tr, 1 /* usetmp */); - if (error == 0) { - if (twe_report_request(tr)) - error = EIO; - } - -out: - if (tr != NULL) - twe_release_request(tr); - if (param != NULL) *** 3487 LINES SKIPPED ***