Skip to content

Commit 5ed9b35

Browse files
committed
Merge tag 'nvme-5.14-2021-06-22' of git://git.infradead.org/nvme into for-5.14/drivers
Pull NVMe updates from Christoph "nvme updates for Linux 5.14: - move the ACPI StorageD3 code to drivers/acpi/ and add quirks for certain AMD CPUs (Mario Limonciello) - zoned device support for nvmet (Chaitanya Kulkarni) - fix the rules for changing the serial number in nvmet (Noam Gottlieb) - various small fixes and cleanups (Dan Carpenter, JK Kim, Chaitanya Kulkarni, Hannes Reinecke, Wesley Sheng, Geert Uytterhoeven, Daniel Wagner)" * tag 'nvme-5.14-2021-06-22' of git://git.infradead.org/nvme: (38 commits) nvmet: use NVMET_MAX_NAMESPACES to set nn value nvme.h: add missing nvme_lba_range_type endianness annotations nvme: remove zeroout memset call for struct nvme-pci: remove zeroout memset call for struct nvmet: remove zeroout memset call for struct nvmet: add ZBD over ZNS backend support nvmet: add Command Set Identifier support nvmet: add nvmet_req_bio put helper for backends nvmet: add req cns error complete helper block: export blk_next_bio() nvmet: remove local variable nvmet: use nvme status value directly nvmet: use u32 type for the local variable nsid nvmet: use u32 for nvmet_subsys max_nsid nvmet: use req->cmd directly in file-ns fast path nvmet: use req->cmd directly in bdev-ns fast path nvmet: make ver stable once connection established nvmet: allow mn change if subsys not discovered nvmet: make sn stable once connection was established nvmet: change sn size and check validity ...
2 parents 2b9ac22 + 3c3ee16 commit 5ed9b35

28 files changed

+1073
-228
lines changed

block/blk-lib.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ struct bio *blk_next_bio(struct bio *bio, unsigned int nr_pages, gfp_t gfp)
2121

2222
return new;
2323
}
24+
EXPORT_SYMBOL_GPL(blk_next_bio);
2425

2526
int __blkdev_issue_discard(struct block_device *bdev, sector_t sector,
2627
sector_t nr_sects, gfp_t gfp_mask, int flags,

drivers/acpi/device_pm.c

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1340,4 +1340,36 @@ int acpi_dev_pm_attach(struct device *dev, bool power_on)
13401340
return 1;
13411341
}
13421342
EXPORT_SYMBOL_GPL(acpi_dev_pm_attach);
1343+
1344+
/**
1345+
* acpi_storage_d3 - Check if D3 should be used in the suspend path
1346+
* @dev: Device to check
1347+
*
1348+
* Return %true if the platform firmware wants @dev to be programmed
1349+
* into D3hot or D3cold (if supported) in the suspend path, or %false
1350+
* when there is no specific preference. On some platforms, if this
1351+
* hint is ignored, @dev may remain unresponsive after suspending the
1352+
* platform as a whole.
1353+
*
1354+
* Although the property has storage in the name it actually is
1355+
* applied to the PCIe slot and plugging in a non-storage device the
1356+
* same platform restrictions will likely apply.
1357+
*/
1358+
bool acpi_storage_d3(struct device *dev)
1359+
{
1360+
struct acpi_device *adev = ACPI_COMPANION(dev);
1361+
u8 val;
1362+
1363+
if (force_storage_d3())
1364+
return true;
1365+
1366+
if (!adev)
1367+
return false;
1368+
if (fwnode_property_read_u8(acpi_fwnode_handle(adev), "StorageD3Enable",
1369+
&val))
1370+
return false;
1371+
return val == 1;
1372+
}
1373+
EXPORT_SYMBOL_GPL(acpi_storage_d3);
1374+
13431375
#endif /* CONFIG_PM */

drivers/acpi/internal.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -236,6 +236,15 @@ static inline int suspend_nvs_save(void) { return 0; }
236236
static inline void suspend_nvs_restore(void) {}
237237
#endif
238238

239+
#ifdef CONFIG_X86
240+
bool force_storage_d3(void);
241+
#else
242+
static inline bool force_storage_d3(void)
243+
{
244+
return false;
245+
}
246+
#endif
247+
239248
/*--------------------------------------------------------------------------
240249
Device properties
241250
-------------------------------------------------------------------------- */

drivers/acpi/x86/utils.c

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -135,3 +135,28 @@ bool acpi_device_always_present(struct acpi_device *adev)
135135

136136
return ret;
137137
}
138+
139+
/*
140+
* AMD systems from Renoir and Lucienne *require* that the NVME controller
141+
* is put into D3 over a Modern Standby / suspend-to-idle cycle.
142+
*
143+
* This is "typically" accomplished using the `StorageD3Enable`
144+
* property in the _DSD that is checked via the `acpi_storage_d3` function
145+
* but this property was introduced after many of these systems launched
146+
* and most OEM systems don't have it in their BIOS.
147+
*
148+
* The Microsoft documentation for StorageD3Enable mentioned that Windows has
149+
* a hardcoded allowlist for D3 support, which was used for these platforms.
150+
*
151+
* This allows quirking on Linux in a similar fashion.
152+
*/
153+
static const struct x86_cpu_id storage_d3_cpu_ids[] = {
154+
X86_MATCH_VENDOR_FAM_MODEL(AMD, 23, 96, NULL), /* Renoir */
155+
X86_MATCH_VENDOR_FAM_MODEL(AMD, 23, 104, NULL), /* Lucienne */
156+
{}
157+
};
158+
159+
bool force_storage_d3(void)
160+
{
161+
return x86_match_cpu(storage_d3_cpu_ids);
162+
}

drivers/nvme/host/Kconfig

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ config NVME_MULTIPATH
2121
help
2222
This option enables support for multipath access to NVMe
2323
subsystems. If this option is enabled only a single
24-
/dev/nvmeXnY device will show up for each NVMe namespaces,
24+
/dev/nvmeXnY device will show up for each NVMe namespace,
2525
even if it is accessible through multiple controllers.
2626

2727
config NVME_HWMON

drivers/nvme/host/core.c

Lines changed: 6 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -721,9 +721,7 @@ EXPORT_SYMBOL_GPL(__nvme_check_ready);
721721

722722
static int nvme_toggle_streams(struct nvme_ctrl *ctrl, bool enable)
723723
{
724-
struct nvme_command c;
725-
726-
memset(&c, 0, sizeof(c));
724+
struct nvme_command c = { };
727725

728726
c.directive.opcode = nvme_admin_directive_send;
729727
c.directive.nsid = cpu_to_le32(NVME_NSID_ALL);
@@ -748,9 +746,8 @@ static int nvme_enable_streams(struct nvme_ctrl *ctrl)
748746
static int nvme_get_stream_params(struct nvme_ctrl *ctrl,
749747
struct streams_directive_params *s, u32 nsid)
750748
{
751-
struct nvme_command c;
749+
struct nvme_command c = { };
752750

753-
memset(&c, 0, sizeof(c));
754751
memset(s, 0, sizeof(*s));
755752

756753
c.directive.opcode = nvme_admin_directive_recv;
@@ -1460,10 +1457,9 @@ static int nvme_features(struct nvme_ctrl *dev, u8 op, unsigned int fid,
14601457
unsigned int dword11, void *buffer, size_t buflen, u32 *result)
14611458
{
14621459
union nvme_result res = { 0 };
1463-
struct nvme_command c;
1460+
struct nvme_command c = { };
14641461
int ret;
14651462

1466-
memset(&c, 0, sizeof(c));
14671463
c.features.opcode = op;
14681464
c.features.fid = cpu_to_le32(fid);
14691465
c.features.dword11 = cpu_to_le32(dword11);
@@ -1591,9 +1587,8 @@ int nvme_getgeo(struct block_device *bdev, struct hd_geometry *geo)
15911587
static void nvme_init_integrity(struct gendisk *disk, u16 ms, u8 pi_type,
15921588
u32 max_integrity_segments)
15931589
{
1594-
struct blk_integrity integrity;
1590+
struct blk_integrity integrity = { };
15951591

1596-
memset(&integrity, 0, sizeof(integrity));
15971592
switch (pi_type) {
15981593
case NVME_NS_DPS_PI_TYPE3:
15991594
integrity.profile = &t10_pi_type3_crc;
@@ -1964,13 +1959,12 @@ static int nvme_send_ns_pr_command(struct nvme_ns *ns, struct nvme_command *c,
19641959
static int nvme_pr_command(struct block_device *bdev, u32 cdw10,
19651960
u64 key, u64 sa_key, u8 op)
19661961
{
1967-
struct nvme_command c;
1962+
struct nvme_command c = { };
19681963
u8 data[16] = { 0, };
19691964

19701965
put_unaligned_le64(key, &data[0]);
19711966
put_unaligned_le64(sa_key, &data[8]);
19721967

1973-
memset(&c, 0, sizeof(c));
19741968
c.common.opcode = op;
19751969
c.common.cdw10 = cpu_to_le32(cdw10);
19761970

@@ -2042,9 +2036,8 @@ int nvme_sec_submit(void *data, u16 spsp, u8 secp, void *buffer, size_t len,
20422036
bool send)
20432037
{
20442038
struct nvme_ctrl *ctrl = data;
2045-
struct nvme_command cmd;
2039+
struct nvme_command cmd = { };
20462040

2047-
memset(&cmd, 0, sizeof(cmd));
20482041
if (send)
20492042
cmd.common.opcode = nvme_admin_security_send;
20502043
else

drivers/nvme/host/fabrics.c

Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -190,11 +190,10 @@ EXPORT_SYMBOL_GPL(nvmf_reg_read32);
190190
*/
191191
int nvmf_reg_read64(struct nvme_ctrl *ctrl, u32 off, u64 *val)
192192
{
193-
struct nvme_command cmd;
193+
struct nvme_command cmd = { };
194194
union nvme_result res;
195195
int ret;
196196

197-
memset(&cmd, 0, sizeof(cmd));
198197
cmd.prop_get.opcode = nvme_fabrics_command;
199198
cmd.prop_get.fctype = nvme_fabrics_type_property_get;
200199
cmd.prop_get.attrib = 1;
@@ -236,10 +235,9 @@ EXPORT_SYMBOL_GPL(nvmf_reg_read64);
236235
*/
237236
int nvmf_reg_write32(struct nvme_ctrl *ctrl, u32 off, u32 val)
238237
{
239-
struct nvme_command cmd;
238+
struct nvme_command cmd = { };
240239
int ret;
241240

242-
memset(&cmd, 0, sizeof(cmd));
243241
cmd.prop_set.opcode = nvme_fabrics_command;
244242
cmd.prop_set.fctype = nvme_fabrics_type_property_set;
245243
cmd.prop_set.attrib = 0;
@@ -364,12 +362,11 @@ static void nvmf_log_connect_error(struct nvme_ctrl *ctrl,
364362
*/
365363
int nvmf_connect_admin_queue(struct nvme_ctrl *ctrl)
366364
{
367-
struct nvme_command cmd;
365+
struct nvme_command cmd = { };
368366
union nvme_result res;
369367
struct nvmf_connect_data *data;
370368
int ret;
371369

372-
memset(&cmd, 0, sizeof(cmd));
373370
cmd.connect.opcode = nvme_fabrics_command;
374371
cmd.connect.fctype = nvme_fabrics_type_connect;
375372
cmd.connect.qid = 0;
@@ -432,12 +429,11 @@ EXPORT_SYMBOL_GPL(nvmf_connect_admin_queue);
432429
*/
433430
int nvmf_connect_io_queue(struct nvme_ctrl *ctrl, u16 qid, bool poll)
434431
{
435-
struct nvme_command cmd;
432+
struct nvme_command cmd = { };
436433
struct nvmf_connect_data *data;
437434
union nvme_result res;
438435
int ret;
439436

440-
memset(&cmd, 0, sizeof(cmd));
441437
cmd.connect.opcode = nvme_fabrics_command;
442438
cmd.connect.fctype = nvme_fabrics_type_connect;
443439
cmd.connect.qid = cpu_to_le16(qid);

drivers/nvme/host/fc.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3111,7 +3111,7 @@ nvme_fc_create_association(struct nvme_fc_ctrl *ctrl)
31113111
}
31123112

31133113
/* FC-NVME supports normal SGL Data Block Descriptors */
3114-
if (!(ctrl->ctrl.sgls & ((1 << 0) | (1 << 1)))) {
3114+
if (!nvme_ctrl_sgl_supported(&ctrl->ctrl)) {
31153115
dev_err(ctrl->ctrl.device,
31163116
"Mandatory sgls are not supported!\n");
31173117
goto out_disconnect_admin_queue;

drivers/nvme/host/ioctl.c

Lines changed: 16 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -177,6 +177,20 @@ static int nvme_submit_io(struct nvme_ns *ns, struct nvme_user_io __user *uio)
177177
metadata, meta_len, lower_32_bits(io.slba), NULL, 0);
178178
}
179179

180+
static bool nvme_validate_passthru_nsid(struct nvme_ctrl *ctrl,
181+
struct nvme_ns *ns, __u32 nsid)
182+
{
183+
if (ns && nsid != ns->head->ns_id) {
184+
dev_err(ctrl->device,
185+
"%s: nsid (%u) in cmd does not match nsid (%u)"
186+
"of namespace\n",
187+
current->comm, nsid, ns->head->ns_id);
188+
return false;
189+
}
190+
191+
return true;
192+
}
193+
180194
static int nvme_user_cmd(struct nvme_ctrl *ctrl, struct nvme_ns *ns,
181195
struct nvme_passthru_cmd __user *ucmd)
182196
{
@@ -192,12 +206,8 @@ static int nvme_user_cmd(struct nvme_ctrl *ctrl, struct nvme_ns *ns,
192206
return -EFAULT;
193207
if (cmd.flags)
194208
return -EINVAL;
195-
if (ns && cmd.nsid != ns->head->ns_id) {
196-
dev_err(ctrl->device,
197-
"%s: nsid (%u) in cmd does not match nsid (%u) of namespace\n",
198-
current->comm, cmd.nsid, ns->head->ns_id);
209+
if (!nvme_validate_passthru_nsid(ctrl, ns, cmd.nsid))
199210
return -EINVAL;
200-
}
201211

202212
memset(&c, 0, sizeof(c));
203213
c.common.opcode = cmd.opcode;
@@ -242,12 +252,8 @@ static int nvme_user_cmd64(struct nvme_ctrl *ctrl, struct nvme_ns *ns,
242252
return -EFAULT;
243253
if (cmd.flags)
244254
return -EINVAL;
245-
if (ns && cmd.nsid != ns->head->ns_id) {
246-
dev_err(ctrl->device,
247-
"%s: nsid (%u) in cmd does not match nsid (%u) of namespace\n",
248-
current->comm, cmd.nsid, ns->head->ns_id);
255+
if (!nvme_validate_passthru_nsid(ctrl, ns, cmd.nsid))
249256
return -EINVAL;
250-
}
251257

252258
memset(&c, 0, sizeof(c));
253259
c.common.opcode = cmd.opcode;

drivers/nvme/host/multipath.c

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -435,11 +435,6 @@ static void nvme_requeue_work(struct work_struct *work)
435435
next = bio->bi_next;
436436
bio->bi_next = NULL;
437437

438-
/*
439-
* Reset disk to the mpath node and resubmit to select a new
440-
* path.
441-
*/
442-
bio_set_dev(bio, head->disk->part0);
443438
submit_bio_noacct(bio);
444439
}
445440
}
@@ -818,6 +813,13 @@ int nvme_mpath_init_identify(struct nvme_ctrl *ctrl, struct nvme_id_ctrl *id)
818813
!(ctrl->subsys->cmic & NVME_CTRL_CMIC_ANA))
819814
return 0;
820815

816+
if (!ctrl->max_namespaces ||
817+
ctrl->max_namespaces > le32_to_cpu(id->nn)) {
818+
dev_err(ctrl->device,
819+
"Invalid MNAN value %u\n", ctrl->max_namespaces);
820+
return -EINVAL;
821+
}
822+
821823
ctrl->anacap = id->anacap;
822824
ctrl->anatt = id->anatt;
823825
ctrl->nanagrpid = le32_to_cpu(id->nanagrpid);

0 commit comments

Comments
 (0)