From owner-svn-src-all@FreeBSD.ORG Sun May 3 07:43:59 2015 Return-Path: Delivered-To: svn-src-all@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by hub.freebsd.org (Postfix) with ESMTPS id 8A911578; Sun, 3 May 2015 07:43:59 +0000 (UTC) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:1900:2254:2068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mx1.freebsd.org (Postfix) with ESMTPS id 78B321ED3; Sun, 3 May 2015 07:43:59 +0000 (UTC) Received: from svn.freebsd.org ([127.0.1.70]) by svn.freebsd.org (8.14.9/8.14.9) with ESMTP id t437hxpW012181; Sun, 3 May 2015 07:43:59 GMT (envelope-from mav@FreeBSD.org) Received: (from mav@localhost) by svn.freebsd.org (8.14.9/8.14.9/Submit) id t437hxsT012180; Sun, 3 May 2015 07:43:59 GMT (envelope-from mav@FreeBSD.org) Message-Id: <201505030743.t437hxsT012180@svn.freebsd.org> X-Authentication-Warning: svn.freebsd.org: mav set sender to mav@FreeBSD.org using -f From: Alexander Motin Date: Sun, 3 May 2015 07:43:59 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r282364 - head/usr.sbin/bhyve X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.20 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 03 May 2015 07:43:59 -0000 Author: mav Date: Sun May 3 07:43:58 2015 New Revision: 282364 URL: https://svnweb.freebsd.org/changeset/base/282364 Log: Implement basic PxTFD.STS.BSY reporting. MFC after: 2 weeks Modified: head/usr.sbin/bhyve/pci_ahci.c Modified: head/usr.sbin/bhyve/pci_ahci.c ============================================================================== --- head/usr.sbin/bhyve/pci_ahci.c Sun May 3 07:18:06 2015 (r282363) +++ head/usr.sbin/bhyve/pci_ahci.c Sun May 3 07:43:58 2015 (r282364) @@ -269,22 +269,24 @@ ahci_write_fis(struct ahci_port *p, enum case FIS_TYPE_REGD2H: offset = 0x40; len = 20; - irq = AHCI_P_IX_DHR; + irq = (fis[1] & (1 << 6)) ? AHCI_P_IX_DHR : 0; break; case FIS_TYPE_SETDEVBITS: offset = 0x58; len = 8; - irq = AHCI_P_IX_SDB; + irq = (fis[1] & (1 << 6)) ? AHCI_P_IX_SDB : 0; break; case FIS_TYPE_PIOSETUP: offset = 0x20; len = 20; - irq = 0; + irq = (fis[1] & (1 << 6)) ? AHCI_P_IX_PS : 0; break; default: WPRINTF("unsupported fis type %d\n", ft); return; } + if (fis[2] & ATA_S_ERROR) + irq |= AHCI_P_IX_TFE; memcpy(p->rfis + offset, fis, len); if (irq) { p->is |= irq; @@ -309,22 +311,23 @@ ahci_write_fis_sdb(struct ahci_port *p, uint8_t error; error = (tfd >> 8) & 0xff; + tfd &= 0x77; memset(fis, 0, sizeof(fis)); fis[0] = FIS_TYPE_SETDEVBITS; fis[1] = (1 << 6); - fis[2] = tfd & 0x77; + fis[2] = tfd; fis[3] = error; if (fis[2] & ATA_S_ERROR) { - p->is |= AHCI_P_IX_TFE; p->err_cfis[0] = slot; - p->err_cfis[2] = tfd & 0x77; + p->err_cfis[2] = tfd; p->err_cfis[3] = error; memcpy(&p->err_cfis[4], cfis + 4, 16); } else { *(uint32_t *)(fis + 4) = (1 << slot); p->sact &= ~(1 << slot); } - p->tfd = tfd; + p->tfd &= ~0x77; + p->tfd |= tfd; ahci_write_fis(p, FIS_TYPE_SETDEVBITS, fis); } @@ -351,7 +354,6 @@ ahci_write_fis_d2h(struct ahci_port *p, fis[12] = cfis[12]; fis[13] = cfis[13]; if (fis[2] & ATA_S_ERROR) { - p->is |= AHCI_P_IX_TFE; p->err_cfis[0] = 0x80; p->err_cfis[2] = tfd & 0xff; p->err_cfis[3] = error; @@ -363,6 +365,21 @@ ahci_write_fis_d2h(struct ahci_port *p, } static void +ahci_write_fis_d2h_ncq(struct ahci_port *p, int slot) +{ + uint8_t fis[20]; + + p->tfd = ATA_S_READY | ATA_S_DSC; + memset(fis, 0, sizeof(fis)); + fis[0] = FIS_TYPE_REGD2H; + fis[1] = 0; /* No interrupt */ + fis[2] = p->tfd; /* Status */ + fis[3] = 0; /* No error */ + p->ci &= ~(1 << slot); + ahci_write_fis(p, FIS_TYPE_REGD2H, fis); +} + +static void ahci_write_reset_fis_d2h(struct ahci_port *p) { uint8_t fis[20]; @@ -589,12 +606,13 @@ ahci_handle_rw(struct ahci_port *p, int struct ahci_cmd_hdr *hdr; uint64_t lba; uint32_t len; - int err, ncq, readop; + int err, first, ncq, readop; prdt = (struct ahci_prdt_entry *)(cfis + 0x80); hdr = (struct ahci_cmd_hdr *)(p->cmd_lst + slot * AHCI_CL_SIZE); ncq = 0; readop = 1; + first = (done == 0); if (cfis[2] == ATA_WRITE || cfis[2] == ATA_WRITE48 || cfis[2] == ATA_WRITE_MUL || cfis[2] == ATA_WRITE_MUL48 || @@ -655,14 +673,14 @@ ahci_handle_rw(struct ahci_port *p, int /* Stuff request onto busy list. */ TAILQ_INSERT_HEAD(&p->iobhd, aior, io_blist); + if (ncq && first) + ahci_write_fis_d2h_ncq(p, slot); + if (readop) err = blockif_read(p->bctx, breq); else err = blockif_write(p->bctx, breq); assert(err == 0); - - if (ncq) - p->ci &= ~(1 << slot); } static void @@ -735,15 +753,18 @@ ahci_handle_dsm_trim(struct ahci_port *p uint8_t *entry; uint64_t elba; uint32_t len, elen; - int err; + int err, first, ncq; uint8_t buf[512]; + first = (done == 0); if (cfis[2] == ATA_DATA_SET_MANAGEMENT) { len = (uint16_t)cfis[13] << 8 | cfis[12]; len *= 512; + ncq = 0; } else { /* ATA_SEND_FPDMA_QUEUED */ len = (uint16_t)cfis[11] << 8 | cfis[3]; len *= 512; + ncq = 1; } read_prdt(p, slot, cfis, buf, sizeof(buf)); @@ -793,6 +814,9 @@ next: */ TAILQ_INSERT_HEAD(&p->iobhd, aior, io_blist); + if (ncq && first) + ahci_write_fis_d2h_ncq(p, slot); + err = blockif_delete(p->bctx, breq); assert(err == 0); } @@ -1548,6 +1572,7 @@ static void ahci_handle_cmd(struct ahci_port *p, int slot, uint8_t *cfis) { + p->tfd |= ATA_S_BUSY; switch (cfis[2]) { case ATA_ATA_IDENTIFY: handle_identify(p, slot, cfis);