diff options
| author | nonaka <nonaka@NetBSD.org> | 2018-04-18 10:11:44 +0000 |
|---|---|---|
| committer | nonaka <nonaka@NetBSD.org> | 2018-04-18 10:11:44 +0000 |
| commit | 433840f4e26d94f82dcfba05df0355207709fbba (patch) | |
| tree | e99481a7510143a84806b18472a5f774a1104a7d /sys/dev | |
| parent | 447ace79c52e862b73e736baed7641706f143296 (diff) | |
nvmectl(8): Add big-endian support.
from FreeBSD nvmecontolr(8) r329824.
Diffstat (limited to 'sys/dev')
| -rw-r--r-- | sys/dev/ic/ld_nvme.c | 8 | ||||
| -rw-r--r-- | sys/dev/ic/nvme.c | 39 | ||||
| -rw-r--r-- | sys/dev/ic/nvmeio.h | 104 |
3 files changed, 127 insertions, 24 deletions
diff --git a/sys/dev/ic/ld_nvme.c b/sys/dev/ic/ld_nvme.c index 257bb72c60b..1ae85bb3aa3 100644 --- a/sys/dev/ic/ld_nvme.c +++ b/sys/dev/ic/ld_nvme.c @@ -1,4 +1,4 @@ -/* $NetBSD: ld_nvme.c,v 1.19 2018/03/16 23:31:19 jdolecek Exp $ */ +/* $NetBSD: ld_nvme.c,v 1.20 2018/04/18 10:11:45 nonaka Exp $ */ /*- * Copyright (C) 2016 NONAKA Kimihiro <nonaka@netbsd.org> @@ -26,7 +26,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: ld_nvme.c,v 1.19 2018/03/16 23:31:19 jdolecek Exp $"); +__KERNEL_RCSID(0, "$NetBSD: ld_nvme.c,v 1.20 2018/04/18 10:11:45 nonaka Exp $"); #include <sys/param.h> #include <sys/systm.h> @@ -86,7 +86,6 @@ ld_nvme_attach(device_t parent, device_t self, void *aux) struct nvme_attach_args *naa = aux; struct nvme_namespace *ns; struct nvm_namespace_format *f; - uint64_t nsze; int error; ld->sc_dv = self; @@ -104,11 +103,10 @@ ld_nvme_attach(device_t parent, device_t self, void *aux) ns = nvme_ns_get(sc->sc_nvme, sc->sc_nsid); KASSERT(ns); - nsze = lemtoh64(&ns->ident->nsze); f = &ns->ident->lbaf[NVME_ID_NS_FLBAS(ns->ident->flbas)]; ld->sc_secsize = 1 << f->lbads; - ld->sc_secperunit = nsze; + ld->sc_secperunit = ns->ident->nsze; ld->sc_maxxfer = naa->naa_maxphys; ld->sc_maxqueuecnt = naa->naa_qentries; ld->sc_start = ld_nvme_start; diff --git a/sys/dev/ic/nvme.c b/sys/dev/ic/nvme.c index f634ddba40f..8ad414dba34 100644 --- a/sys/dev/ic/nvme.c +++ b/sys/dev/ic/nvme.c @@ -1,4 +1,4 @@ -/* $NetBSD: nvme.c,v 1.38 2018/04/18 10:05:59 nonaka Exp $ */ +/* $NetBSD: nvme.c,v 1.39 2018/04/18 10:11:45 nonaka Exp $ */ /* $OpenBSD: nvme.c,v 1.49 2016/04/18 05:59:50 dlg Exp $ */ /* @@ -18,7 +18,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: nvme.c,v 1.38 2018/04/18 10:05:59 nonaka Exp $"); +__KERNEL_RCSID(0, "$NetBSD: nvme.c,v 1.39 2018/04/18 10:11:45 nonaka Exp $"); #include <sys/param.h> #include <sys/systm.h> @@ -624,7 +624,9 @@ nvme_ns_identify(struct nvme_softc *sc, uint16_t nsid) identify = kmem_zalloc(sizeof(*identify), KM_SLEEP); *identify = *((volatile struct nvm_identify_namespace *)NVME_DMA_KVA(mem)); - //memcpy(identify, NVME_DMA_KVA(mem), sizeof(*identify)); + + /* Convert data to host endian */ + nvme_identify_namespace_swapbytes(identify); ns = nvme_ns_get(sc, nsid); KASSERT(ns); @@ -899,7 +901,7 @@ nvme_getcache_fill(struct nvme_queue *q, struct nvme_ccb *ccb, void *slot) struct nvme_sqe *sqe = slot; sqe->opcode = NVM_ADMIN_GET_FEATURES; - sqe->cdw10 = NVM_FEATURE_VOLATILE_WRITE_CACHE; + htolem32(&sqe->cdw10, NVM_FEATURE_VOLATILE_WRITE_CACHE); } static void @@ -1122,7 +1124,7 @@ nvme_q_submit(struct nvme_softc *sc, struct nvme_queue *q, struct nvme_ccb *ccb, sizeof(*sqe) * tail, sizeof(*sqe), BUS_DMASYNC_POSTWRITE); memset(sqe, 0, sizeof(*sqe)); (*fill)(q, ccb, sqe); - sqe->cid = ccb->ccb_id; + htolem16(&sqe->cid, ccb->ccb_id); bus_dmamap_sync(sc->sc_dmat, NVME_DMA_MAP(q->q_sq_dmamem), sizeof(*sqe) * tail, sizeof(*sqe), BUS_DMASYNC_PREWRITE); @@ -1334,25 +1336,28 @@ nvme_identify(struct nvme_softc *sc, u_int mps) goto done; identify = NVME_DMA_KVA(mem); - - strnvisx(sn, sizeof(sn), (const char *)identify->sn, - sizeof(identify->sn), VIS_TRIM|VIS_SAFE|VIS_OCTAL); - strnvisx(mn, sizeof(mn), (const char *)identify->mn, - sizeof(identify->mn), VIS_TRIM|VIS_SAFE|VIS_OCTAL); - strnvisx(fr, sizeof(fr), (const char *)identify->fr, - sizeof(identify->fr), VIS_TRIM|VIS_SAFE|VIS_OCTAL); + sc->sc_identify = *identify; + identify = NULL; + + /* Convert data to host endian */ + nvme_identify_controller_swapbytes(&sc->sc_identify); + + strnvisx(sn, sizeof(sn), (const char *)sc->sc_identify.sn, + sizeof(sc->sc_identify.sn), VIS_TRIM|VIS_SAFE|VIS_OCTAL); + strnvisx(mn, sizeof(mn), (const char *)sc->sc_identify.mn, + sizeof(sc->sc_identify.mn), VIS_TRIM|VIS_SAFE|VIS_OCTAL); + strnvisx(fr, sizeof(fr), (const char *)sc->sc_identify.fr, + sizeof(sc->sc_identify.fr), VIS_TRIM|VIS_SAFE|VIS_OCTAL); aprint_normal_dev(sc->sc_dev, "%s, firmware %s, serial %s\n", mn, fr, sn); - if (identify->mdts > 0) { - mdts = (1 << identify->mdts) * (1 << mps); + if (sc->sc_identify.mdts > 0) { + mdts = (1 << sc->sc_identify.mdts) * (1 << mps); if (mdts < sc->sc_mdts) sc->sc_mdts = mdts; } - sc->sc_nn = lemtoh32(&identify->nn); - - memcpy(&sc->sc_identify, identify, sizeof(sc->sc_identify)); + sc->sc_nn = sc->sc_identify.nn; done: nvme_dmamem_free(sc, mem); diff --git a/sys/dev/ic/nvmeio.h b/sys/dev/ic/nvmeio.h index dbfe8e9970f..52500543eca 100644 --- a/sys/dev/ic/nvmeio.h +++ b/sys/dev/ic/nvmeio.h @@ -1,4 +1,4 @@ -/* $NetBSD: nvmeio.h,v 1.1 2016/06/04 16:11:51 nonaka Exp $ */ +/* $NetBSD: nvmeio.h,v 1.2 2018/04/18 10:11:45 nonaka Exp $ */ /*- * Copyright (C) 2012-2013 Intel Corporation @@ -25,12 +25,13 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $FreeBSD: head/sys/dev/nvme/nvme.h 296617 2016-03-10 17:13:10Z mav $ + * $FreeBSD: head/sys/dev/nvme/nvme.h 329824 2018-02-22 13:32:31Z wma $ */ #ifndef __NVMEIO_H__ #define __NVMEIO_H__ +#include <sys/endian.h> #include <sys/ioccom.h> #include <dev/ic/nvmereg.h> @@ -94,4 +95,103 @@ struct nvme_pt_command { uint32_t timeout; }; +/* Endianess conversion functions for NVMe structs */ +static inline void +nvme_le128toh(uint64_t v[2]) +{ +#if _BYTE_ORDER != _LITTLE_ENDIAN + uint64_t t; + + t = le64toh(v[0]); + v[0] = le64toh(v[1]); + v[1] = t; +#endif +} + +static inline void +nvme_namespace_format_swapbytes(struct nvm_namespace_format *format) +{ + +#if _BYTE_ORDER != _LITTLE_ENDIAN + format->ms = le16toh(format->ms); +#endif +} + +static inline void +nvme_identify_namespace_swapbytes(struct nvm_identify_namespace *identify) +{ +#if _BYTE_ORDER != _LITTLE_ENDIAN + u_int i; + + identify->nsze = le64toh(identify->nsze); + identify->ncap = le64toh(identify->ncap); + identify->nuse = le64toh(identify->nuse); + identify->nawun = le16toh(identify->nawun); + identify->nawupf = le16toh(identify->nawupf); + identify->nacwu = le16toh(identify->nacwu); + identify->nabsn = le16toh(identify->nabsn); + identify->nabo = le16toh(identify->nabo); + identify->nabspf = le16toh(identify->nabspf); + identify->noiob = le16toh(identify->noiob); + for (i = 0; i < __arraycount(identify->lbaf); i++) + nvme_namespace_format_swapbytes(&identify->lbaf[i]); +#endif +} + +static inline void +nvme_identify_psd_swapbytes(struct nvm_identify_psd *psd) +{ + +#if _BYTE_ORDER != _LITTLE_ENDIAN + psd->mp = le16toh(psd->mp); + psd->enlat = le32toh(psd->enlat); + psd->exlat = le32toh(psd->exlat); + psd->idlp = le16toh(psd->idlp); + psd->actp = le16toh(psd->actp); + psd->ap = le16toh(psd->ap); +#endif +} + +static inline void +nvme_identify_controller_swapbytes(struct nvm_identify_controller *identify) +{ +#if _BYTE_ORDER != _LITTLE_ENDIAN + u_int i; + + identify->vid = le16toh(identify->vid); + identify->ssvid = le16toh(identify->ssvid); + identify->cntlid = le16toh(identify->cntlid); + identify->ver = le32toh(identify->ver); + identify->rtd3r = le32toh(identify->rtd3r); + identify->rtd3e = le32toh(identify->rtd3e); + identify->oaes = le32toh(identify->oaes); + identify->ctrattr = le32toh(identify->ctrattr); + identify->oacs = le16toh(identify->oacs); + identify->wctemp = le16toh(identify->wctemp); + identify->cctemp = le16toh(identify->cctemp); + identify->mtfa = le16toh(identify->mtfa); + identify->hmpre = le32toh(identify->hmpre); + identify->hmmin = le32toh(identify->hmmin); + nvme_le128toh(identify->untncap.tnvmcap); + nvme_le128toh(identify->untncap.unvmcap); + identify->rpmbs = le32toh(identify->rpmbs); + identify->edstt = le16toh(identify->edstt); + identify->kas = le16toh(identify->kas); + identify->hctma = le16toh(identify->hctma); + identify->mntmt = le16toh(identify->mntmt); + identify->mxtmt = le16toh(identify->mxtmt); + identify->sanicap = le32toh(identify->sanicap); + identify->maxcmd = le16toh(identify->maxcmd); + identify->nn = le32toh(identify->nn); + identify->oncs = le16toh(identify->oncs); + identify->fuses = le16toh(identify->fuses); + identify->awun = le16toh(identify->awun); + identify->awupf = le16toh(identify->awupf); + identify->acwu = le16toh(identify->acwu); + identify->sgls = le32toh(identify->sgls); + for (i = 0; i < __arraycount(identify->psd); i++) + nvme_identify_psd_swapbytes(&identify->psd[i]); +#endif +} + #endif /* __NVMEIO_H__ */ |
