zephyr/drivers/disk/nvme/nvme_helpers.h
Tomasz Bursztyka 95b8493857 drivers/nvme: Return an error in case of non dword-aligned data buffer
This is a specific case for NVMe where given data buffer pointers must
be dword (4 bytes) aligned.

There is no virtual memory management between the user thread and NVMe
driver (which one could detect such wrong alignement on physical memory
and thus reallocate the memory properly, so it would be fully
transparent for the user thread), thus the need to push that check to
the user.

This has been going under the radar so far as Qemu does not seem to
follow NVMe specifications where PRP1 (in DPTR) must always be
dword-aligned. It really does not follow the rule: specifications
details that if bits 1:0 of PRP1 are set, the controller may generate
an error or treat the address as if these bits were unset. Seems like
a bug in Qemu, I did not check the code there however.

Signed-off-by: Tomasz Bursztyka <tomasz.bursztyka@linux.intel.com>
2023-09-22 09:23:18 +02:00

520 lines
20 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/*
* SPDX-License-Identifier: Apache-2.0
* Copyright (c) 2022 Intel Corp.
*/
#ifndef ZEPHYR_DRIVERS_DISK_NVME_NHME_HELPERS_H_
#define ZEPHYR_DRIVERS_DISK_NVME_NHME_HELPERS_H_
#define NVME_GONE 0xfffffffful
/*
* Macros to deal with NVME revisions, as defined VS register
*/
#define NVME_REV(x, y) (((x) << 16) | ((y) << 8))
#define NVME_MAJOR(r) (((r) >> 16) & 0xffff)
#define NVME_MINOR(r) (((r) >> 8) & 0xff)
/*
* Use to mark a command to apply to all namespaces, or to retrieve global
* log pages.
*/
#define NVME_GLOBAL_NAMESPACE_TAG ((uint32_t)0xFFFFFFFF)
/* Many items are expressed in terms of power of two times MPS */
#define NVME_MPS_SHIFT 12
/* Register field definitions */
#define NVME_CAP_LO_REG_MQES_SHIFT (0)
#define NVME_CAP_LO_REG_MQES_MASK (0xFFFF)
#define NVME_CAP_LO_REG_CQR_SHIFT (16)
#define NVME_CAP_LO_REG_CQR_MASK (0x1)
#define NVME_CAP_LO_REG_AMS_SHIFT (17)
#define NVME_CAP_LO_REG_AMS_MASK (0x3)
#define NVME_CAP_LO_REG_TO_SHIFT (24)
#define NVME_CAP_LO_REG_TO_MASK (0xFF)
#define NVME_CAP_LO_MQES(x) \
(((x) >> NVME_CAP_LO_REG_MQES_SHIFT) & NVME_CAP_LO_REG_MQES_MASK)
#define NVME_CAP_LO_CQR(x) \
(((x) >> NVME_CAP_LO_REG_CQR_SHIFT) & NVME_CAP_LO_REG_CQR_MASK)
#define NVME_CAP_LO_AMS(x) \
(((x) >> NVME_CAP_LO_REG_AMS_SHIFT) & NVME_CAP_LO_REG_AMS_MASK)
#define NVME_CAP_LO_TO(x) \
(((x) >> NVME_CAP_LO_REG_TO_SHIFT) & NVME_CAP_LO_REG_TO_MASK)
#define NVME_CAP_HI_REG_DSTRD_SHIFT (0)
#define NVME_CAP_HI_REG_DSTRD_MASK (0xF)
#define NVME_CAP_HI_REG_NSSRS_SHIFT (4)
#define NVME_CAP_HI_REG_NSSRS_MASK (0x1)
#define NVME_CAP_HI_REG_CSS_SHIFT (5)
#define NVME_CAP_HI_REG_CSS_MASK (0xff)
#define NVME_CAP_HI_REG_CSS_NVM_SHIFT (5)
#define NVME_CAP_HI_REG_CSS_NVM_MASK (0x1)
#define NVME_CAP_HI_REG_BPS_SHIFT (13)
#define NVME_CAP_HI_REG_BPS_MASK (0x1)
#define NVME_CAP_HI_REG_MPSMIN_SHIFT (16)
#define NVME_CAP_HI_REG_MPSMIN_MASK (0xF)
#define NVME_CAP_HI_REG_MPSMAX_SHIFT (20)
#define NVME_CAP_HI_REG_MPSMAX_MASK (0xF)
#define NVME_CAP_HI_REG_PMRS_SHIFT (24)
#define NVME_CAP_HI_REG_PMRS_MASK (0x1)
#define NVME_CAP_HI_REG_CMBS_SHIFT (25)
#define NVME_CAP_HI_REG_CMBS_MASK (0x1)
#define NVME_CAP_HI_DSTRD(x) \
(((x) >> NVME_CAP_HI_REG_DSTRD_SHIFT) & NVME_CAP_HI_REG_DSTRD_MASK)
#define NVME_CAP_HI_NSSRS(x) \
(((x) >> NVME_CAP_HI_REG_NSSRS_SHIFT) & NVME_CAP_HI_REG_NSSRS_MASK)
#define NVME_CAP_HI_CSS(x) \
(((x) >> NVME_CAP_HI_REG_CSS_SHIFT) & NVME_CAP_HI_REG_CSS_MASK)
#define NVME_CAP_HI_CSS_NVM(x) \
(((x) >> NVME_CAP_HI_REG_CSS_NVM_SHIFT) & NVME_CAP_HI_REG_CSS_NVM_MASK)
#define NVME_CAP_HI_BPS(x) \
(((x) >> NVME_CAP_HI_REG_BPS_SHIFT) & NVME_CAP_HI_REG_BPS_MASK)
#define NVME_CAP_HI_MPSMIN(x) \
(((x) >> NVME_CAP_HI_REG_MPSMIN_SHIFT) & NVME_CAP_HI_REG_MPSMIN_MASK)
#define NVME_CAP_HI_MPSMAX(x) \
(((x) >> NVME_CAP_HI_REG_MPSMAX_SHIFT) & NVME_CAP_HI_REG_MPSMAX_MASK)
#define NVME_CAP_HI_PMRS(x) \
(((x) >> NVME_CAP_HI_REG_PMRS_SHIFT) & NVME_CAP_HI_REG_PMRS_MASK)
#define NVME_CAP_HI_CMBS(x) \
(((x) >> NVME_CAP_HI_REG_CMBS_SHIFT) & NVME_CAP_HI_REG_CMBS_MASK)
#define NVME_CC_REG_EN_SHIFT (0)
#define NVME_CC_REG_EN_MASK (0x1)
#define NVME_CC_REG_CSS_SHIFT (4)
#define NVME_CC_REG_CSS_MASK (0x7)
#define NVME_CC_REG_MPS_SHIFT (7)
#define NVME_CC_REG_MPS_MASK (0xF)
#define NVME_CC_REG_AMS_SHIFT (11)
#define NVME_CC_REG_AMS_MASK (0x7)
#define NVME_CC_REG_SHN_SHIFT (14)
#define NVME_CC_REG_SHN_MASK (0x3)
#define NVME_CC_REG_IOSQES_SHIFT (16)
#define NVME_CC_REG_IOSQES_MASK (0xF)
#define NVME_CC_REG_IOCQES_SHIFT (20)
#define NVME_CC_REG_IOCQES_MASK (0xF)
#define NVME_CSTS_REG_RDY_SHIFT (0)
#define NVME_CSTS_REG_RDY_MASK (0x1)
#define NVME_CSTS_REG_CFS_SHIFT (1)
#define NVME_CSTS_REG_CFS_MASK (0x1)
#define NVME_CSTS_REG_SHST_SHIFT (2)
#define NVME_CSTS_REG_SHST_MASK (0x3)
#define NVME_CSTS_REG_NVSRO_SHIFT (4)
#define NVME_CSTS_REG_NVSRO_MASK (0x1)
#define NVME_CSTS_REG_PP_SHIFT (5)
#define NVME_CSTS_REG_PP_MASK (0x1)
#define NVME_CSTS_GET_SHST(csts) \
(((csts) >> NVME_CSTS_REG_SHST_SHIFT) & NVME_CSTS_REG_SHST_MASK)
#define NVME_AQA_REG_ASQS_SHIFT (0)
#define NVME_AQA_REG_ASQS_MASK (0xFFF)
#define NVME_AQA_REG_ACQS_SHIFT (16)
#define NVME_AQA_REG_ACQS_MASK (0xFFF)
#define NVME_PMRCAP_REG_RDS_SHIFT (3)
#define NVME_PMRCAP_REG_RDS_MASK (0x1)
#define NVME_PMRCAP_REG_WDS_SHIFT (4)
#define NVME_PMRCAP_REG_WDS_MASK (0x1)
#define NVME_PMRCAP_REG_BIR_SHIFT (5)
#define NVME_PMRCAP_REG_BIR_MASK (0x7)
#define NVME_PMRCAP_REG_PMRTU_SHIFT (8)
#define NVME_PMRCAP_REG_PMRTU_MASK (0x3)
#define NVME_PMRCAP_REG_PMRWBM_SHIFT (10)
#define NVME_PMRCAP_REG_PMRWBM_MASK (0xf)
#define NVME_PMRCAP_REG_PMRTO_SHIFT (16)
#define NVME_PMRCAP_REG_PMRTO_MASK (0xff)
#define NVME_PMRCAP_REG_CMSS_SHIFT (24)
#define NVME_PMRCAP_REG_CMSS_MASK (0x1)
#define NVME_PMRCAP_RDS(x) \
(((x) >> NVME_PMRCAP_REG_RDS_SHIFT) & NVME_PMRCAP_REG_RDS_MASK)
#define NVME_PMRCAP_WDS(x) \
(((x) >> NVME_PMRCAP_REG_WDS_SHIFT) & NVME_PMRCAP_REG_WDS_MASK)
#define NVME_PMRCAP_BIR(x) \
(((x) >> NVME_PMRCAP_REG_BIR_SHIFT) & NVME_PMRCAP_REG_BIR_MASK)
#define NVME_PMRCAP_PMRTU(x) \
(((x) >> NVME_PMRCAP_REG_PMRTU_SHIFT) & NVME_PMRCAP_REG_PMRTU_MASK)
#define NVME_PMRCAP_PMRWBM(x) \
(((x) >> NVME_PMRCAP_REG_PMRWBM_SHIFT) & NVME_PMRCAP_REG_PMRWBM_MASK)
#define NVME_PMRCAP_PMRTO(x) \
(((x) >> NVME_PMRCAP_REG_PMRTO_SHIFT) & NVME_PMRCAP_REG_PMRTO_MASK)
#define NVME_PMRCAP_CMSS(x) \
(((x) >> NVME_PMRCAP_REG_CMSS_SHIFT) & NVME_PMRCAP_REG_CMSS_MASK)
/* Command field definitions */
#define NVME_CMD_FUSE_SHIFT (8)
#define NVME_CMD_FUSE_MASK (0x3)
#define NVME_STATUS_P_SHIFT (0)
#define NVME_STATUS_P_MASK (0x1)
#define NVME_STATUS_SC_SHIFT (1)
#define NVME_STATUS_SC_MASK (0xFF)
#define NVME_STATUS_SCT_SHIFT (9)
#define NVME_STATUS_SCT_MASK (0x7)
#define NVME_STATUS_CRD_SHIFT (12)
#define NVME_STATUS_CRD_MASK (0x3)
#define NVME_STATUS_M_SHIFT (14)
#define NVME_STATUS_M_MASK (0x1)
#define NVME_STATUS_DNR_SHIFT (15)
#define NVME_STATUS_DNR_MASK (0x1)
#define NVME_STATUS_GET_P(st) \
(((st) >> NVME_STATUS_P_SHIFT) & NVME_STATUS_P_MASK)
#define NVME_STATUS_GET_SC(st) \
(((st) >> NVME_STATUS_SC_SHIFT) & NVME_STATUS_SC_MASK)
#define NVME_STATUS_GET_SCT(st) \
(((st) >> NVME_STATUS_SCT_SHIFT) & NVME_STATUS_SCT_MASK)
#define NVME_STATUS_GET_CRD(st) \
(((st) >> NVME_STATUS_CRD_SHIFT) & NVME_STATUS_CRD_MASK)
#define NVME_STATUS_GET_M(st) \
(((st) >> NVME_STATUS_M_SHIFT) & NVME_STATUS_M_MASK)
#define NVME_STATUS_GET_DNR(st) \
(((st) >> NVME_STATUS_DNR_SHIFT) & NVME_STATUS_DNR_MASK)
/** Controller Multi-path I/O and Namespace Sharing Capabilities */
/* More then one port */
#define NVME_CTRLR_DATA_MIC_MPORTS_SHIFT (0)
#define NVME_CTRLR_DATA_MIC_MPORTS_MASK (0x1)
/* More then one controller */
#define NVME_CTRLR_DATA_MIC_MCTRLRS_SHIFT (1)
#define NVME_CTRLR_DATA_MIC_MCTRLRS_MASK (0x1)
/* SR-IOV Virtual Function */
#define NVME_CTRLR_DATA_MIC_SRIOVVF_SHIFT (2)
#define NVME_CTRLR_DATA_MIC_SRIOVVF_MASK (0x1)
/* Asymmetric Namespace Access Reporting */
#define NVME_CTRLR_DATA_MIC_ANAR_SHIFT (3)
#define NVME_CTRLR_DATA_MIC_ANAR_MASK (0x1)
/** OAES - Optional Asynchronous Events Supported */
/* supports Namespace Attribute Notices event */
#define NVME_CTRLR_DATA_OAES_NS_ATTR_SHIFT (8)
#define NVME_CTRLR_DATA_OAES_NS_ATTR_MASK (0x1)
/* supports Firmware Activation Notices event */
#define NVME_CTRLR_DATA_OAES_FW_ACTIVATE_SHIFT (9)
#define NVME_CTRLR_DATA_OAES_FW_ACTIVATE_MASK (0x1)
/* supports Asymmetric Namespace Access Change Notices event */
#define NVME_CTRLR_DATA_OAES_ASYM_NS_CHANGE_SHIFT (11)
#define NVME_CTRLR_DATA_OAES_ASYM_NS_CHANGE_MASK (0x1)
/* supports Predictable Latency Event Aggregate Log Change Notices event */
#define NVME_CTRLR_DATA_OAES_PREDICT_LATENCY_SHIFT (12)
#define NVME_CTRLR_DATA_OAES_PREDICT_LATENCY_MASK (0x1)
/* supports LBA Status Information Notices event */
#define NVME_CTRLR_DATA_OAES_LBA_STATUS_SHIFT (13)
#define NVME_CTRLR_DATA_OAES_LBA_STATUS_MASK (0x1)
/* supports Endurance Group Event Aggregate Log Page Changes Notices event */
#define NVME_CTRLR_DATA_OAES_ENDURANCE_GROUP_SHIFT (14)
#define NVME_CTRLR_DATA_OAES_ENDURANCE_GROUP_MASK (0x1)
/* supports Normal NVM Subsystem Shutdown event */
#define NVME_CTRLR_DATA_OAES_NORMAL_SHUTDOWN_SHIFT (15)
#define NVME_CTRLR_DATA_OAES_NORMAL_SHUTDOWN_MASK (0x1)
/* supports Zone Descriptor Changed Notices event */
#define NVME_CTRLR_DATA_OAES_ZONE_DESC_CHANGE_SHIFT (27)
#define NVME_CTRLR_DATA_OAES_ZONE_DESC_CHANGE_MASK (0x1)
/* supports Discovery Log Page Change Notification event */
#define NVME_CTRLR_DATA_OAES_LOG_PAGE_CHANGE_SHIFT (31)
#define NVME_CTRLR_DATA_OAES_LOG_PAGE_CHANGE_MASK (0x1)
/** OACS - optional admin command support */
/* supports security send/receive commands */
#define NVME_CTRLR_DATA_OACS_SECURITY_SHIFT (0)
#define NVME_CTRLR_DATA_OACS_SECURITY_MASK (0x1)
/* supports format nvm command */
#define NVME_CTRLR_DATA_OACS_FORMAT_SHIFT (1)
#define NVME_CTRLR_DATA_OACS_FORMAT_MASK (0x1)
/* supports firmware activate/download commands */
#define NVME_CTRLR_DATA_OACS_FIRMWARE_SHIFT (2)
#define NVME_CTRLR_DATA_OACS_FIRMWARE_MASK (0x1)
/* supports namespace management commands */
#define NVME_CTRLR_DATA_OACS_NSMGMT_SHIFT (3)
#define NVME_CTRLR_DATA_OACS_NSMGMT_MASK (0x1)
/* supports Device Self-test command */
#define NVME_CTRLR_DATA_OACS_SELFTEST_SHIFT (4)
#define NVME_CTRLR_DATA_OACS_SELFTEST_MASK (0x1)
/* supports Directives */
#define NVME_CTRLR_DATA_OACS_DIRECTIVES_SHIFT (5)
#define NVME_CTRLR_DATA_OACS_DIRECTIVES_MASK (0x1)
/* supports NVMe-MI Send/Receive */
#define NVME_CTRLR_DATA_OACS_NVMEMI_SHIFT (6)
#define NVME_CTRLR_DATA_OACS_NVMEMI_MASK (0x1)
/* supports Virtualization Management */
#define NVME_CTRLR_DATA_OACS_VM_SHIFT (7)
#define NVME_CTRLR_DATA_OACS_VM_MASK (0x1)
/* supports Doorbell Buffer Config */
#define NVME_CTRLR_DATA_OACS_DBBUFFER_SHIFT (8)
#define NVME_CTRLR_DATA_OACS_DBBUFFER_MASK (0x1)
/* supports Get LBA Status */
#define NVME_CTRLR_DATA_OACS_GETLBA_SHIFT (9)
#define NVME_CTRLR_DATA_OACS_GETLBA_MASK (0x1)
/** firmware updates */
/* first slot is read-only */
#define NVME_CTRLR_DATA_FRMW_SLOT1_RO_SHIFT (0)
#define NVME_CTRLR_DATA_FRMW_SLOT1_RO_MASK (0x1)
/* number of firmware slots */
#define NVME_CTRLR_DATA_FRMW_NUM_SLOTS_SHIFT (1)
#define NVME_CTRLR_DATA_FRMW_NUM_SLOTS_MASK (0x7)
/* firmware activation without reset */
#define NVME_CTRLR_DATA_FRMW_ACT_WO_RESET_SHIFT (4)
#define NVME_CTRLR_DATA_FRMW_ACT_WO_RESET_MASK (0x1)
/** log page attributes */
/* per namespace smart/health log page */
#define NVME_CTRLR_DATA_LPA_NS_SMART_SHIFT (0)
#define NVME_CTRLR_DATA_LPA_NS_SMART_MASK (0x1)
/** AVSCC - admin vendor specific command configuration */
/* admin vendor specific commands use spec format */
#define NVME_CTRLR_DATA_AVSCC_SPEC_FORMAT_SHIFT (0)
#define NVME_CTRLR_DATA_AVSCC_SPEC_FORMAT_MASK (0x1)
/** Autonomous Power State Transition Attributes */
/* Autonomous Power State Transitions supported */
#define NVME_CTRLR_DATA_APSTA_APST_SUPP_SHIFT (0)
#define NVME_CTRLR_DATA_APSTA_APST_SUPP_MASK (0x1)
/** Sanitize Capabilities */
/* Crypto Erase Support */
#define NVME_CTRLR_DATA_SANICAP_CES_SHIFT (0)
#define NVME_CTRLR_DATA_SANICAP_CES_MASK (0x1)
/* Block Erase Support */
#define NVME_CTRLR_DATA_SANICAP_BES_SHIFT (1)
#define NVME_CTRLR_DATA_SANICAP_BES_MASK (0x1)
/* Overwrite Support */
#define NVME_CTRLR_DATA_SANICAP_OWS_SHIFT (2)
#define NVME_CTRLR_DATA_SANICAP_OWS_MASK (0x1)
/* No-Deallocate Inhibited */
#define NVME_CTRLR_DATA_SANICAP_NDI_SHIFT (29)
#define NVME_CTRLR_DATA_SANICAP_NDI_MASK (0x1)
/* No-Deallocate Modifies Media After Sanitize */
#define NVME_CTRLR_DATA_SANICAP_NODMMAS_SHIFT (30)
#define NVME_CTRLR_DATA_SANICAP_NODMMAS_MASK (0x3)
#define NVME_CTRLR_DATA_SANICAP_NODMMAS_UNDEF (0)
#define NVME_CTRLR_DATA_SANICAP_NODMMAS_NO (1)
#define NVME_CTRLR_DATA_SANICAP_NODMMAS_YES (2)
/** submission queue entry size */
#define NVME_CTRLR_DATA_SQES_MIN_SHIFT (0)
#define NVME_CTRLR_DATA_SQES_MIN_MASK (0xF)
#define NVME_CTRLR_DATA_SQES_MAX_SHIFT (4)
#define NVME_CTRLR_DATA_SQES_MAX_MASK (0xF)
/** completion queue entry size */
#define NVME_CTRLR_DATA_CQES_MIN_SHIFT (0)
#define NVME_CTRLR_DATA_CQES_MIN_MASK (0xF)
#define NVME_CTRLR_DATA_CQES_MAX_SHIFT (4)
#define NVME_CTRLR_DATA_CQES_MAX_MASK (0xF)
/** optional nvm command support */
#define NVME_CTRLR_DATA_ONCS_COMPARE_SHIFT (0)
#define NVME_CTRLR_DATA_ONCS_COMPARE_MASK (0x1)
#define NVME_CTRLR_DATA_ONCS_WRITE_UNC_SHIFT (1)
#define NVME_CTRLR_DATA_ONCS_WRITE_UNC_MASK (0x1)
#define NVME_CTRLR_DATA_ONCS_DSM_SHIFT (2)
#define NVME_CTRLR_DATA_ONCS_DSM_MASK (0x1)
#define NVME_CTRLR_DATA_ONCS_WRZERO_SHIFT (3)
#define NVME_CTRLR_DATA_ONCS_WRZERO_MASK (0x1)
#define NVME_CTRLR_DATA_ONCS_SAVEFEAT_SHIFT (4)
#define NVME_CTRLR_DATA_ONCS_SAVEFEAT_MASK (0x1)
#define NVME_CTRLR_DATA_ONCS_RESERV_SHIFT (5)
#define NVME_CTRLR_DATA_ONCS_RESERV_MASK (0x1)
#define NVME_CTRLR_DATA_ONCS_TIMESTAMP_SHIFT (6)
#define NVME_CTRLR_DATA_ONCS_TIMESTAMP_MASK (0x1)
#define NVME_CTRLR_DATA_ONCS_VERIFY_SHIFT (7)
#define NVME_CTRLR_DATA_ONCS_VERIFY_MASK (0x1)
/** Fused Operation Support */
#define NVME_CTRLR_DATA_FUSES_CNW_SHIFT (0)
#define NVME_CTRLR_DATA_FUSES_CNW_MASK (0x1)
/** Format NVM Attributes */
#define NVME_CTRLR_DATA_FNA_FORMAT_ALL_SHIFT (0)
#define NVME_CTRLR_DATA_FNA_FORMAT_ALL_MASK (0x1)
#define NVME_CTRLR_DATA_FNA_ERASE_ALL_SHIFT (1)
#define NVME_CTRLR_DATA_FNA_ERASE_ALL_MASK (0x1)
#define NVME_CTRLR_DATA_FNA_CRYPTO_ERASE_SHIFT (2)
#define NVME_CTRLR_DATA_FNA_CRYPTO_ERASE_MASK (0x1)
/** volatile write cache */
/* volatile write cache present */
#define NVME_CTRLR_DATA_VWC_PRESENT_SHIFT (0)
#define NVME_CTRLR_DATA_VWC_PRESENT_MASK (0x1)
/* flush all namespaces supported */
#define NVME_CTRLR_DATA_VWC_ALL_SHIFT (1)
#define NVME_CTRLR_DATA_VWC_ALL_MASK (0x3)
#define NVME_CTRLR_DATA_VWC_ALL_UNKNOWN (0)
#define NVME_CTRLR_DATA_VWC_ALL_NO (2)
#define NVME_CTRLR_DATA_VWC_ALL_YES (3)
/** namespace features */
/* thin provisioning */
#define NVME_NS_DATA_NSFEAT_THIN_PROV_SHIFT (0)
#define NVME_NS_DATA_NSFEAT_THIN_PROV_MASK (0x1)
/* NAWUN, NAWUPF, and NACWU fields are valid */
#define NVME_NS_DATA_NSFEAT_NA_FIELDS_SHIFT (1)
#define NVME_NS_DATA_NSFEAT_NA_FIELDS_MASK (0x1)
/* Deallocated or Unwritten Logical Block errors supported */
#define NVME_NS_DATA_NSFEAT_DEALLOC_SHIFT (2)
#define NVME_NS_DATA_NSFEAT_DEALLOC_MASK (0x1)
/* NGUID and EUI64 fields are not reusable */
#define NVME_NS_DATA_NSFEAT_NO_ID_REUSE_SHIFT (3)
#define NVME_NS_DATA_NSFEAT_NO_ID_REUSE_MASK (0x1)
/* NPWG, NPWA, NPDG, NPDA, and NOWS are valid */
#define NVME_NS_DATA_NSFEAT_NPVALID_SHIFT (4)
#define NVME_NS_DATA_NSFEAT_NPVALID_MASK (0x1)
/** formatted lba size */
#define NVME_NS_DATA_FLBAS_FORMAT_SHIFT (0)
#define NVME_NS_DATA_FLBAS_FORMAT_MASK (0xF)
#define NVME_NS_DATA_FLBAS_EXTENDED_SHIFT (4)
#define NVME_NS_DATA_FLBAS_EXTENDED_MASK (0x1)
/** metadata capabilities */
/* metadata can be transferred as part of data prp list */
#define NVME_NS_DATA_MC_EXTENDED_SHIFT (0)
#define NVME_NS_DATA_MC_EXTENDED_MASK (0x1)
/* metadata can be transferred with separate metadata pointer */
#define NVME_NS_DATA_MC_POINTER_SHIFT (1)
#define NVME_NS_DATA_MC_POINTER_MASK (0x1)
/** end-to-end data protection capabilities */
/* protection information type 1 */
#define NVME_NS_DATA_DPC_PIT1_SHIFT (0)
#define NVME_NS_DATA_DPC_PIT1_MASK (0x1)
/* protection information type 2 */
#define NVME_NS_DATA_DPC_PIT2_SHIFT (1)
#define NVME_NS_DATA_DPC_PIT2_MASK (0x1)
/* protection information type 3 */
#define NVME_NS_DATA_DPC_PIT3_SHIFT (2)
#define NVME_NS_DATA_DPC_PIT3_MASK (0x1)
/* first eight bytes of metadata */
#define NVME_NS_DATA_DPC_MD_START_SHIFT (3)
#define NVME_NS_DATA_DPC_MD_START_MASK (0x1)
/* last eight bytes of metadata */
#define NVME_NS_DATA_DPC_MD_END_SHIFT (4)
#define NVME_NS_DATA_DPC_MD_END_MASK (0x1)
/** end-to-end data protection type settings */
/* protection information type */
#define NVME_NS_DATA_DPS_PIT_SHIFT (0)
#define NVME_NS_DATA_DPS_PIT_MASK (0x7)
/* 1 == protection info transferred at start of metadata */
/* 0 == protection info transferred at end of metadata */
#define NVME_NS_DATA_DPS_MD_START_SHIFT (3)
#define NVME_NS_DATA_DPS_MD_START_MASK (0x1)
/** Namespace Multi-path I/O and Namespace Sharing Capabilities */
/* the namespace may be attached to two or more controllers */
#define NVME_NS_DATA_NMIC_MAY_BE_SHARED_SHIFT (0)
#define NVME_NS_DATA_NMIC_MAY_BE_SHARED_MASK (0x1)
/** Reservation Capabilities */
/* Persist Through Power Loss */
#define NVME_NS_DATA_RESCAP_PTPL_SHIFT (0)
#define NVME_NS_DATA_RESCAP_PTPL_MASK (0x1)
/* supports the Write Exclusive */
#define NVME_NS_DATA_RESCAP_WR_EX_SHIFT (1)
#define NVME_NS_DATA_RESCAP_WR_EX_MASK (0x1)
/* supports the Exclusive Access */
#define NVME_NS_DATA_RESCAP_EX_AC_SHIFT (2)
#define NVME_NS_DATA_RESCAP_EX_AC_MASK (0x1)
/* supports the Write Exclusive Registrants Only */
#define NVME_NS_DATA_RESCAP_WR_EX_RO_SHIFT (3)
#define NVME_NS_DATA_RESCAP_WR_EX_RO_MASK (0x1)
/* supports the Exclusive Access - Registrants Only */
#define NVME_NS_DATA_RESCAP_EX_AC_RO_SHIFT (4)
#define NVME_NS_DATA_RESCAP_EX_AC_RO_MASK (0x1)
/* supports the Write Exclusive All Registrants */
#define NVME_NS_DATA_RESCAP_WR_EX_AR_SHIFT (5)
#define NVME_NS_DATA_RESCAP_WR_EX_AR_MASK (0x1)
/* supports the Exclusive Access - All Registrants */
#define NVME_NS_DATA_RESCAP_EX_AC_AR_SHIFT (6)
#define NVME_NS_DATA_RESCAP_EX_AC_AR_MASK (0x1)
/* Ignore Existing Key is used as defined in revision 1.3 or later */
#define NVME_NS_DATA_RESCAP_IEKEY13_SHIFT (7)
#define NVME_NS_DATA_RESCAP_IEKEY13_MASK (0x1)
/** Format Progress Indicator */
/* percentage of the Format NVM command that remains to be completed */
#define NVME_NS_DATA_FPI_PERC_SHIFT (0)
#define NVME_NS_DATA_FPI_PERC_MASK (0x7f)
/* namespace supports the Format Progress Indicator */
#define NVME_NS_DATA_FPI_SUPP_SHIFT (7)
#define NVME_NS_DATA_FPI_SUPP_MASK (0x1)
/** Deallocate Logical Block Features */
/* deallocated logical block read behavior */
#define NVME_NS_DATA_DLFEAT_READ_SHIFT (0)
#define NVME_NS_DATA_DLFEAT_READ_MASK (0x07)
#define NVME_NS_DATA_DLFEAT_READ_NR (0x00)
#define NVME_NS_DATA_DLFEAT_READ_00 (0x01)
#define NVME_NS_DATA_DLFEAT_READ_FF (0x02)
/* supports the Deallocate bit in the Write Zeroes */
#define NVME_NS_DATA_DLFEAT_DWZ_SHIFT (3)
#define NVME_NS_DATA_DLFEAT_DWZ_MASK (0x01)
/* Guard field for deallocated logical blocks is set to the CRC */
#define NVME_NS_DATA_DLFEAT_GCRC_SHIFT (4)
#define NVME_NS_DATA_DLFEAT_GCRC_MASK (0x01)
/** lba format support */
/* metadata size */
#define NVME_NS_DATA_LBAF_MS_SHIFT (0)
#define NVME_NS_DATA_LBAF_MS_MASK (0xFFFF)
/* lba data size */
#define NVME_NS_DATA_LBAF_LBADS_SHIFT (16)
#define NVME_NS_DATA_LBAF_LBADS_MASK (0xFF)
/* relative performance */
#define NVME_NS_DATA_LBAF_RP_SHIFT (24)
#define NVME_NS_DATA_LBAF_RP_MASK (0x3)
enum nvme_critical_warning_state {
NVME_CRIT_WARN_ST_AVAILABLE_SPARE = 0x1,
NVME_CRIT_WARN_ST_TEMPERATURE = 0x2,
NVME_CRIT_WARN_ST_DEVICE_RELIABILITY = 0x4,
NVME_CRIT_WARN_ST_READ_ONLY = 0x8,
NVME_CRIT_WARN_ST_VOLATILE_MEMORY_BACKUP = 0x10,
};
#define NVME_CRIT_WARN_ST_RESERVED_MASK (0xE0)
#define NVME_ASYNC_EVENT_NS_ATTRIBUTE (0x100)
#define NVME_ASYNC_EVENT_FW_ACTIVATE (0x200)
/* Helper macro to combine *_MASK and *_SHIFT defines */
#define NVMEB(name) (name##_MASK << name##_SHIFT)
/* CC register SHN field values */
enum shn_value {
NVME_SHN_NORMAL = 0x1,
NVME_SHN_ABRUPT = 0x2,
};
/* CSTS register SHST field values */
enum shst_value {
NVME_SHST_NORMAL = 0x0,
NVME_SHST_OCCURRING = 0x1,
NVME_SHST_COMPLETE = 0x2,
};
#define nvme_mmio_offsetof(reg) \
offsetof(struct nvme_registers, reg)
#define nvme_mmio_read_4(b_a, reg) \
sys_read32((mm_reg_t)b_a + nvme_mmio_offsetof(reg))
#define nvme_mmio_write_4(b_a, reg, val) \
sys_write32(val, (mm_reg_t)b_a + nvme_mmio_offsetof(reg))
#define nvme_mmio_write_8(b_a, reg, val) \
do { \
sys_write32(val & 0xFFFFFFFF, \
(mm_reg_t)b_a + nvme_mmio_offsetof(reg)); \
sys_write32((val & 0xFFFFFFFF00000000ULL) >> 32, \
(mm_reg_t)b_a + nvme_mmio_offsetof(reg) + 4); \
} while (0)
#define NVME_IS_BUFFER_DWORD_ALIGNED(_buf_addr) (!((uintptr_t)_buf_addr & 0x3))
#endif /* ZEPHYR_DRIVERS_DISK_NVME_NHME_HELPERS_H_ */