From: Steven Seungcheol Lee Date: Wed, 8 Dec 2021 06:18:12 +0000 (+0900) Subject: zns: Add support for zone random write area (zrwa) X-Git-Tag: v2.0-rc0~28^2~3 X-Git-Url: https://www.infradead.org/git/?a=commitdiff_plain;h=fcc8a889c8dc6b2d8b573766d6eee087a338ed08;p=users%2Fsagi%2Fnvme-cli.git zns: Add support for zone random write area (zrwa) NVMe - TP 4076 Zoned Random Write Area 2021.08.23 - Ratified Signed-off-by: Steven Seungcheol Lee Co-authored-by: Klaus Jensen --- diff --git a/Documentation/nvme-zns-flush-zone.1 b/Documentation/nvme-zns-flush-zone.1 new file mode 100644 index 00000000..558f119e --- /dev/null +++ b/Documentation/nvme-zns-flush-zone.1 @@ -0,0 +1,84 @@ +'\" t +.\" Title: nvme-zns-flush-zone +.\" Author: [FIXME: author] [see http://docbook.sf.net/el/author] +.\" Generator: DocBook XSL Stylesheets v1.78.1 +.\" Date: 12/08/2021 +.\" Manual: NVMe Manual +.\" Source: NVMe +.\" Language: English +.\" +.TH "NVME\-ZNS\-FLUSH\-ZO" "1" "12/08/2021" "NVMe" "NVMe Manual" +.\" ----------------------------------------------------------------- +.\" * Define some portability stuff +.\" ----------------------------------------------------------------- +.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +.\" http://bugs.debian.org/507673 +.\" http://lists.gnu.org/archive/html/groff/2009-02/msg00013.html +.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +.ie \n(.g .ds Aq \(aq +.el .ds Aq ' +.\" ----------------------------------------------------------------- +.\" * set default formatting +.\" ----------------------------------------------------------------- +.\" disable hyphenation +.nh +.\" disable justification (adjust text to left margin only) +.ad l +.\" ----------------------------------------------------------------- +.\" * MAIN CONTENT STARTS HERE * +.\" ----------------------------------------------------------------- +.SH "NAME" +nvme-zns-flush-zone \- flush zone +.SH "SYNOPSIS" +.sp +.nf +\fInvme zns flush\-zone\fR [\-\-namespace\-id= | \-n ] + [\-\-last\-lba= | \-l ] + [\-\-timeout= | \-t ] +.fi +.SH "DESCRIPTION" +.sp +For the NVMe device given, issues the Zone Management Send command with the "flush Zone" action\&. This will flush the zone that is opened as zone random write area\&. +.sp +The parameter is mandatory and may be either the NVMe character device (ex: /dev/nvme0), or a namespace block device (ex: /dev/nvme0n1)\&. +.SH "OPTIONS" +.PP +\-n , \-\-namespace\-id= +.RS 4 +Use the provided namespace id for the command\&. If not provided, the namespace id of the block device will be used\&. If the command is issued to a non\-block device, the parameter is required\&. +.RE +.PP +\-l , \-\-last\-lba= +.RS 4 +The last LBA of the zone to be flushed\&. +.RE +.PP +\-t , \-\-timeout= +.RS 4 +Override default timeout value\&. In milliseconds\&. +.RE +.SH "EXAMPLES" +.sp +.RS 4 +.ie n \{\ +\h'-04'\(bu\h'+03'\c +.\} +.el \{\ +.sp -1 +.IP \(bu 2.3 +.\} +flush the first zwra of first zone for zrwacg(15) on namespace 1: +.sp +.if n \{\ +.RS 4 +.\} +.nf +# nvme zns flush\-zone /dev/nvme0 \-n 1 \-l 15 +.fi +.if n \{\ +.RE +.\} +.RE +.SH "NVME" +.sp +Part of nvme\-cli diff --git a/Documentation/nvme-zns-flush-zone.html b/Documentation/nvme-zns-flush-zone.html new file mode 100644 index 00000000..e8026dbe --- /dev/null +++ b/Documentation/nvme-zns-flush-zone.html @@ -0,0 +1,838 @@ + + + + + +nvme-zns-flush-zone(1) + + + + + +
+
+

SYNOPSIS

+
+
+
nvme zns flush-zone <device> [--namespace-id=<NUM> | -n <NUM>]
+                               [--last-lba=<LBA> | -l <LBA>]
+                                   [--timeout=<timeout> | -t <timeout> ]
+
+
+
+
+
+

DESCRIPTION

+
+

For the NVMe device given, issues the Zone Management Send command with the +"flush Zone" action. This will flush the zone that is opened as +zone random write area.

+

The <device> parameter is mandatory and may be either the NVMe character +device (ex: /dev/nvme0), or a namespace block device (ex: /dev/nvme0n1).

+
+
+
+

OPTIONS

+
+
+
+-n <NUM> +
+
+--namespace-id=<NUM> +
+
+

+ Use the provided namespace id for the command. If not provided, the + namespace id of the block device will be used. If the command is issued + to a non-block device, the parameter is required. +

+
+
+-l <lba> +
+
+--last-lba=<lba> +
+
+

+ The last LBA of the zone to be flushed. +

+
+
+-t <timeout> +
+
+--timeout=<timeout> +
+
+

+ Override default timeout value. In milliseconds. +

+
+
+
+
+
+

EXAMPLES

+
+
    +
  • +

    +flush the first zwra of first zone for zrwacg(15) on namespace 1: +

    +
    +
    +
    # nvme zns flush-zone /dev/nvme0 -n 1 -l 15
    +
    +
  • +
+
+
+
+

NVME

+
+

Part of nvme-cli

+
+
+
+

+ + + diff --git a/Documentation/nvme-zns-flush-zone.txt b/Documentation/nvme-zns-flush-zone.txt new file mode 100644 index 00000000..f1ee558f --- /dev/null +++ b/Documentation/nvme-zns-flush-zone.txt @@ -0,0 +1,50 @@ +nvme-zns-flush-zone(1) +====================== + +NAME +---- +nvme-zns-flush-zone - flush zone + +SYNOPSIS +-------- +[verse] +'nvme zns flush-zone' [--namespace-id= | -n ] + [--last-lba= | -l ] + [--timeout= | -t ] + +DESCRIPTION +----------- +For the NVMe device given, issues the Zone Management Send command with the +"flush Zone" action. This will flush the zone that is opened as +zone random write area. + +The parameter is mandatory and may be either the NVMe character +device (ex: /dev/nvme0), or a namespace block device (ex: /dev/nvme0n1). + +OPTIONS +------- +-n :: +--namespace-id=:: + Use the provided namespace id for the command. If not provided, the + namespace id of the block device will be used. If the command is issued + to a non-block device, the parameter is required. + +-l :: +--last-lba=:: + The last LBA of the zone to be flushed. + +-t :: +--timeout=:: + Override default timeout value. In milliseconds. + +EXAMPLES +-------- +* flush the first zwra of first zone for zrwacg(15) on namespace 1: ++ +------------ +# nvme zns flush-zone /dev/nvme0 -n 1 -l 15 +------------ + +NVME +---- +Part of nvme-cli diff --git a/Documentation/nvme-zns-open-zone.1 b/Documentation/nvme-zns-open-zone.1 index 99fff88f..037f3fcd 100644 --- a/Documentation/nvme-zns-open-zone.1 +++ b/Documentation/nvme-zns-open-zone.1 @@ -2,12 +2,12 @@ .\" Title: nvme-zns-open-zone .\" Author: [FIXME: author] [see http://docbook.sf.net/el/author] .\" Generator: DocBook XSL Stylesheets v1.78.1 -.\" Date: 08/26/2021 +.\" Date: 12/08/2021 .\" Manual: NVMe Manual .\" Source: NVMe .\" Language: English .\" -.TH "NVME\-ZNS\-OPEN\-ZON" "1" "08/26/2021" "NVMe" "NVMe Manual" +.TH "NVME\-ZNS\-OPEN\-ZON" "1" "12/08/2021" "NVMe" "NVMe Manual" .\" ----------------------------------------------------------------- .\" * Define some portability stuff .\" ----------------------------------------------------------------- @@ -34,6 +34,7 @@ nvme-zns-open-zone \- Opens one or all zones .nf \fInvme zns open\-zone\fR [\-\-namespace\-id= | \-n ] [\-\-start\-lba= | \-s ] + [\-\-zrwa | \-r] [\-\-select\-all | \-a] [\-\-timeout= | \-t ] .fi @@ -54,6 +55,11 @@ Use the provided namespace id for the command\&. If not provided, the namespace The starting LBA of the zone to open\&. .RE .PP +\-r, \-\-zrwa +.RS 4 +Zone Random Write Area Allocation +.RE +.PP \-a, \-\-select\-all .RS 4 Select all zones for this action diff --git a/Documentation/nvme-zns-open-zone.html b/Documentation/nvme-zns-open-zone.html index 62a7e128..b2407355 100644 --- a/Documentation/nvme-zns-open-zone.html +++ b/Documentation/nvme-zns-open-zone.html @@ -748,6 +748,7 @@ nvme-zns-open-zone(1) Manual Page
nvme zns open-zone <device> [--namespace-id=<NUM> | -n <NUM>]
                                                 [--start-lba=<LBA> | -s <LBA>]
+                                                [--zrwa | -r]
                                                 [--select-all | -a]
                                                 [--timeout=<timeout> | -t <timeout>]
@@ -792,6 +793,17 @@ device (ex: /dev/nvme0), or a namespace block device (ex: /dev/nvme0n1).

+-r +
+
+--zrwa +
+
+

+ Zone Random Write Area Allocation +

+
+
-a
@@ -842,7 +854,7 @@ Open the first zone on namespace 1:

diff --git a/Documentation/nvme-zns-open-zone.txt b/Documentation/nvme-zns-open-zone.txt index bf1c9118..420320c6 100644 --- a/Documentation/nvme-zns-open-zone.txt +++ b/Documentation/nvme-zns-open-zone.txt @@ -10,6 +10,7 @@ SYNOPSIS [verse] 'nvme zns open-zone' [--namespace-id= | -n ] [--start-lba= | -s ] + [--zrwa | -r] [--select-all | -a] [--timeout= | -t ] @@ -33,6 +34,10 @@ OPTIONS --start-lba=:: The starting LBA of the zone to open. +-r:: +--zrwa:: + Zone Random Write Area Allocation + -a:: --select-all:: Select all zones for this action diff --git a/Documentation/nvme-zns-set-zone-desc.1 b/Documentation/nvme-zns-set-zone-desc.1 index b3130d6a..bbb6b200 100644 --- a/Documentation/nvme-zns-set-zone-desc.1 +++ b/Documentation/nvme-zns-set-zone-desc.1 @@ -2,12 +2,12 @@ .\" Title: nvme-zns-set-zone-desc .\" Author: [FIXME: author] [see http://docbook.sf.net/el/author] .\" Generator: DocBook XSL Stylesheets v1.78.1 -.\" Date: 08/26/2021 +.\" Date: 12/08/2021 .\" Manual: NVMe Manual .\" Source: NVMe .\" Language: English .\" -.TH "NVME\-ZNS\-SET\-ZONE" "1" "08/26/2021" "NVMe" "NVMe Manual" +.TH "NVME\-ZNS\-SET\-ZONE" "1" "12/08/2021" "NVMe" "NVMe Manual" .\" ----------------------------------------------------------------- .\" * Define some portability stuff .\" ----------------------------------------------------------------- @@ -34,6 +34,7 @@ nvme-zns-set-zone-desc \- Set extended descriptor data for a zone .nf \fInvme zns setzone\-desc\fR [\-\-namespace\-id= | \-n ] [\-\-start\-lba=, \-s ] + [\-\-zrwa | \-r] [\-data=, \-d ] [\-\-timeout= | \-t ] .fi @@ -52,6 +53,11 @@ Use the provided namespace id for the command\&. If not provided, the namespace The starting LBA of the zone to manage send\&. .RE .PP +\-r, \-\-zrwa +.RS 4 +Zone Random Write Area Allocation +.RE +.PP \-d .RS 4 Optional file for data (default stdin) diff --git a/Documentation/nvme-zns-set-zone-desc.html b/Documentation/nvme-zns-set-zone-desc.html index 3fe678b0..b595554b 100644 --- a/Documentation/nvme-zns-set-zone-desc.html +++ b/Documentation/nvme-zns-set-zone-desc.html @@ -748,6 +748,7 @@ nvme-zns-set-zone-desc(1) Manual Page
nvme zns setzone-desc <device> [--namespace-id=<NUM> | -n <NUM>]
                                  [--start-lba=<IONUM>, -s <IONUM>]
+                                 [--zrwa | -r]
                                  [-data=<FILE>, -d <FILE>]
                                  [--timeout=<timeout> | -t <timeout>]
@@ -792,6 +793,17 @@ length will automatically be calculated from the zns identify namesapce.

+-r +
+
+--zrwa +
+
+

+ Zone Random Write Area Allocation +

+
+
-d <FILE
@@ -843,7 +855,7 @@ Write "hello world" into the zone descriptor for namespace 1’s first zone

diff --git a/Documentation/nvme-zns-set-zone-desc.txt b/Documentation/nvme-zns-set-zone-desc.txt index 880d405f..c24afa46 100644 --- a/Documentation/nvme-zns-set-zone-desc.txt +++ b/Documentation/nvme-zns-set-zone-desc.txt @@ -10,6 +10,7 @@ SYNOPSIS [verse] 'nvme zns setzone-desc' [--namespace-id= | -n ] [--start-lba=, -s ] + [--zrwa | -r] [-data=, -d ] [--timeout= | -t ] @@ -32,6 +33,10 @@ OPTIONS --start-lba=:: The starting LBA of the zone to manage send. +-r:: +--zrwa:: + Zone Random Write Area Allocation + -d :: Optional file for data (default stdin) diff --git a/Documentation/nvme-zns-zone-mgmt-send.1 b/Documentation/nvme-zns-zone-mgmt-send.1 index 40725a51..dc8bd2a2 100644 --- a/Documentation/nvme-zns-zone-mgmt-send.1 +++ b/Documentation/nvme-zns-zone-mgmt-send.1 @@ -2,12 +2,12 @@ .\" Title: nvme-zns-zone-mgmt-send .\" Author: [FIXME: author] [see http://docbook.sf.net/el/author] .\" Generator: DocBook XSL Stylesheets v1.78.1 -.\" Date: 08/26/2021 +.\" Date: 12/08/2021 .\" Manual: NVMe Manual .\" Source: NVMe .\" Language: English .\" -.TH "NVME\-ZNS\-ZONE\-MGM" "1" "08/26/2021" "NVMe" "NVMe Manual" +.TH "NVME\-ZNS\-ZONE\-MGM" "1" "12/08/2021" "NVMe" "NVMe Manual" .\" ----------------------------------------------------------------- .\" * Define some portability stuff .\" ----------------------------------------------------------------- @@ -34,10 +34,11 @@ nvme-zns-zone-mgmt-send \- Zone Management Send command .nf \fInvme zns zone\-mgmt\-send\fR [\-\-namespace\-id= | \-n ] [\-\-start\-lba=, \-s ] + [\-\-zsaso, \-o] [\-\-select\-all, \-a] [\-\-zsa=, \-z ] [\-\-data\-len=, \-l ] - [\-data=, \-d ] + [\-\-data=, \-d ] [\-\-timeout= | \-t ] .fi .SH "DESCRIPTION" @@ -60,6 +61,11 @@ The starting LBA of the zone to manage send\&. Send data buffer length .RE .PP +\-o, \-\-zsaso +.RS 4 +Zone Send Action Specific Option +.RE +.PP \-\-select\-all, \-a .RS 4 Send command to all zones @@ -75,7 +81,7 @@ Zone send action\&. Buffer length if data required .RE .PP -\-d +\-d .RS 4 Optional file for data (default stdin) .RE diff --git a/Documentation/nvme-zns-zone-mgmt-send.html b/Documentation/nvme-zns-zone-mgmt-send.html index d74cc256..38329013 100644 --- a/Documentation/nvme-zns-zone-mgmt-send.html +++ b/Documentation/nvme-zns-zone-mgmt-send.html @@ -748,10 +748,11 @@ nvme-zns-zone-mgmt-send(1) Manual Page
nvme zns zone-mgmt-send <device> [--namespace-id=<NUM> | -n <NUM>]
                                    [--start-lba=<IONUM>, -s <IONUM>]
+                                   [--zsaso, -o]
                                    [--select-all, -a]
                                    [--zsa=<NUM>, -z <NUM>]
                                    [--data-len=<IONUM>, -l <IONUM>]
-                                   [-data=<FILE>, -d <FILE>]
+                                   [--data=<FILE>, -d <FILE>]
                                    [--timeout=<timeout> | -t <timeout>]
@@ -806,6 +807,17 @@ Alternatively, the data may come from a file that can be specified.

+-o +
+
+--zsaso +
+
+

+ Zone Send Action Specific Option +

+
+
--select-all
@@ -842,7 +854,7 @@ Alternatively, the data may come from a file that can be specified.

-d <FILE
--data=<FILE> +--data=<FILE>

@@ -900,7 +912,7 @@ Write "hello world" into the zone descriptor for namespace 1’s first zone


diff --git a/Documentation/nvme-zns-zone-mgmt-send.txt b/Documentation/nvme-zns-zone-mgmt-send.txt index bf34d5e6..8cbb5c0b 100644 --- a/Documentation/nvme-zns-zone-mgmt-send.txt +++ b/Documentation/nvme-zns-zone-mgmt-send.txt @@ -10,10 +10,11 @@ SYNOPSIS [verse] 'nvme zns zone-mgmt-send' [--namespace-id= | -n ] [--start-lba=, -s ] + [--zsaso, -o] [--select-all, -a] [--zsa=, -z ] [--data-len=, -l ] - [-data=, -d ] + [--data=, -d ] [--timeout= | -t ] DESCRIPTION @@ -39,6 +40,10 @@ OPTIONS --data-len=:: Send data buffer length +-o:: +--zsaso:: + Zone Send Action Specific Option + --select-all:: -a:: Send command to all zones @@ -52,7 +57,7 @@ OPTIONS Buffer length if data required -d :: +--data=:: Optional file for data (default stdin) -t :: diff --git a/completions/bash-nvme-completion.sh b/completions/bash-nvme-completion.sh index 052566d0..f3812738 100644 --- a/completions/bash-nvme-completion.sh +++ b/completions/bash-nvme-completion.sh @@ -1257,7 +1257,7 @@ plugin_zns_opts () { --data-len= -l" ;; "zone-mgmt-send") - opts+=" --namespace-id= -n --start-lba= -s \ + opts+=" --namespace-id= -n --start-lba= -s --zsaso -o \ --select-all -a --zsa= -z --data-len= -l \ --data= -d --timeout= -t" ;; @@ -1276,7 +1276,7 @@ plugin_zns_opts () { ;; "open-zone") opts+=" --namespace-id= -n --start-lba= -s \ - --select-all -a --timeout= -t" + --select-all -a --timeout= -t --zrwa -r" ;; "reset-zone") opts+=" --namespace-id= -n --start-lba= -s \ @@ -1288,7 +1288,10 @@ plugin_zns_opts () { ;; "set-zone-desc") opts+=" --namespace-id= -n --start-lba= -s \ - --data= -d --timeout= -t" + --data= -d --timeout= -t --zrwa -r" + ;; + "flush-zone") + opts+=" --namespace-id= -n --last-lba= -l --timeout= -t" ;; "zone-append") opts+=" --namespace-id= -n --zslba= -s --data-size= -z \ diff --git a/nvme-print.c b/nvme-print.c index a199073d..12549987 100644 --- a/nvme-print.c +++ b/nvme-print.c @@ -4299,6 +4299,10 @@ static void json_nvme_zns_id_ns(struct nvme_zns_id_ns *ns, json_object_add_value_int(root, "frl1", le32_to_cpu(ns->frl1)); json_object_add_value_int(root, "frl2", le32_to_cpu(ns->frl2)); json_object_add_value_int(root, "frl3", le32_to_cpu(ns->frl3)); + json_object_add_value_int(root, "numzrwa", le32_to_cpu(ns->numzrwa)); + json_object_add_value_int(root, "zrwafg", le16_to_cpu(ns->zrwafg)); + json_object_add_value_int(root, "zrwasz", le16_to_cpu(ns->zrwasz)); + json_object_add_value_int(root, "zrwacap", ns->zrwacap); lbafs = json_create_array(); json_object_add_value_array(root, "lbafe", lbafs); @@ -4335,13 +4339,16 @@ static void show_nvme_id_ns_zoned_zoc(__le16 ns_zoc) static void show_nvme_id_ns_zoned_ozcs(__le16 ns_ozcs) { __u16 ozcs = le16_to_cpu(ns_ozcs); - __u8 rsvd = (ozcs & 0xfffe) >> 1; + __u8 rsvd = (ozcs & 0xfffc) >> 2; __u8 razb = ozcs & 0x1; + __u8 zrwasup = (ozcs & 0x2) >> 1; if (rsvd) printf(" [15:1] : %#x\tReserved\n", rsvd); printf(" [0:0] : %#x\t Read Across Zone Boundaries: %s\n", razb, razb ? "Yes" : "No"); + printf(" [1:1] : %#x\tZone Random Write Area: %sSupported\n", zrwasup, + zrwasup ? "" : "Not "); } static void nvme_show_zns_id_ns_recommandeded_limit(__le32 ns_rl, int human, @@ -4354,6 +4361,17 @@ static void nvme_show_zns_id_ns_recommandeded_limit(__le32 ns_rl, int human, printf("%s : %u\n", target_limit, recommandeded_limit); } +static void nvme_show_zns_id_ns_zrwacap(__u8 zrwacap) +{ + __u8 rsvd = (zrwacap & 0xfe) >> 1; + __u8 expflushsup = zrwacap & 0x1; + + if (rsvd) + printf(" [7:1] : %#x\tReserved\n", rsvd); + printf(" [0:0] : %#x\t Explicit ZRWA Flush %sSupported\n", + expflushsup, expflushsup ? "" : "Not "); +} + void nvme_show_zns_id_ns(struct nvme_zns_id_ns *ns, struct nvme_id_ns *id_ns, unsigned long flags) { @@ -4411,6 +4429,16 @@ void nvme_show_zns_id_ns(struct nvme_zns_id_ns *ns, nvme_show_zns_id_ns_recommandeded_limit(ns->frl, human, "frl2"); nvme_show_zns_id_ns_recommandeded_limit(ns->frl, human, "frl3"); + printf("numzrwa : %u\n", le32_to_cpu(ns->numzrwa)); + printf("zrwafg : %u\n", le16_to_cpu(ns->zrwafg)); + printf("zrwasz : %u\n", le16_to_cpu(ns->zrwasz)); + if (human) { + printf("zrwacap : %u\tZone Random Write Area Capability\n", ns->zrwacap); + nvme_show_zns_id_ns_zrwacap(ns->zrwacap); + } else { + printf("zrwacap : %u\n", ns->zrwacap); + } + for (i = 0; i <= id_ns->nlbaf; i++){ if (human) printf("LBA Format Extension %2d : Zone Size: 0x%"PRIx64" LBAs - " diff --git a/plugins/zns/zns.c b/plugins/zns/zns.c index 17283110..066aa0f1 100644 --- a/plugins/zns/zns.c +++ b/plugins/zns/zns.c @@ -225,14 +225,14 @@ close_fd: return nvme_status_to_errno(err, false); } -static int __zns_mgmt_send(int fd, __u32 namespace_id, __u64 zslba, +static int __zns_mgmt_send(int fd, __u32 namespace_id, __u64 zslba, __u8 zsaso, bool select_all, __u32 timeout, enum nvme_zns_send_action zsa, __u32 data_len, void *buf) { int err; - - err = nvme_zns_mgmt_send(fd, namespace_id, zslba, zsa, select_all, + err = nvme_zns_mgmt_send(fd, namespace_id, zslba, zsa, select_all, zsaso, data_len, buf, timeout, NULL); + close(fd); return err; } @@ -280,7 +280,7 @@ static int zns_mgmt_send(int argc, char **argv, struct command *cmd, struct plug } } - err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zslba, + err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zslba, 0, cfg.select_all, cfg.timeout, zsa, 0, NULL); if (!err) printf("%s: Success, action:%d zone:%"PRIx64" all:%d nsid:%d\n", @@ -330,7 +330,9 @@ static int get_zdes_bytes(int fd, __u32 nsid) static int zone_mgmt_send(int argc, char **argv, struct command *cmd, struct plugin *plugin) { const char *desc = "Zone Management Send"; - const char *zslba = "starting LBA of the zone for this command"; + const char *zslba = "starting LBA of the zone for this command"\ + "(for flush action, last lba to flush)"; + const char *zsaso = "Zone Send Action Specific Option"; const char *select_all = "send command to all zones"; const char *zsa = "zone send action"; const char *data_len = "buffer length if data required"; @@ -343,6 +345,7 @@ static int zone_mgmt_send(int argc, char **argv, struct command *cmd, struct plu struct config { __u64 zslba; __u32 namespace_id; + __u8 zsaso; bool select_all; __u8 zsa; int data_len; @@ -355,6 +358,7 @@ static int zone_mgmt_send(int argc, char **argv, struct command *cmd, struct plu OPT_ARGS(opts) = { OPT_UINT("namespace-id", 'n', &cfg.namespace_id, namespace_id), OPT_SUFFIX("start-lba", 's', &cfg.zslba, zslba), + OPT_FLAG("zsaso", 'o', &cfg.zsaso, zsaso), OPT_FLAG("select-all", 'a', &cfg.select_all, select_all), OPT_BYTE("zsa", 'z', &cfg.zsa, zsa), OPT_UINT("data-len", 'l', &cfg.data_len, data_len), @@ -423,8 +427,8 @@ static int zone_mgmt_send(int argc, char **argv, struct command *cmd, struct plu } } - err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zslba, cfg.select_all, - cfg.timeout, cfg.zsa, cfg.data_len, buf); + err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zslba, cfg.zsaso, + cfg.select_all, cfg.timeout, cfg.zsa, cfg.data_len, buf); if (!err) printf("zone-mgmt-send: Success, action:%d zone:%"PRIx64" " "all:%d nsid:%d\n", @@ -462,8 +466,55 @@ static int finish_zone(int argc, char **argv, struct command *cmd, struct plugin static int open_zone(int argc, char **argv, struct command *cmd, struct plugin *plugin) { const char *desc = "Open zones\n"; + const char *zslba = "starting LBA of the zone for this command"; + const char *zrwa = "Zone Random Write Area Allocation"; + const char *select_all = "send command to all zones"; + const char *timeout = "timeout value, in milliseconds"; + + int err, fd; + + struct config { + __u64 zslba; + __u32 namespace_id; + bool zrwa; + bool select_all; + __u32 timeout; + }; + + struct config cfg = { + }; + + OPT_ARGS(opts) = { + OPT_UINT("namespace-id", 'n', &cfg.namespace_id, namespace_id), + OPT_SUFFIX("start-lba", 's', &cfg.zslba, zslba), + OPT_FLAG("zrwa", 'r', &cfg.zrwa, zrwa), + OPT_FLAG("select-all", 'a', &cfg.select_all, select_all), + OPT_UINT("timeout", 't', &cfg.timeout, timeout), + OPT_END() + }; - return zns_mgmt_send(argc, argv, cmd, plugin, desc, NVME_ZNS_ZSA_OPEN); + fd = parse_and_open(argc, argv, desc, opts); + if (fd < 0) + return errno; + + if (!cfg.namespace_id) { + err = nvme_get_nsid(fd, &cfg.namespace_id); + if (err < 0) { + perror("get-namespace-id"); + goto close_fd; + } + } + + err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zslba, cfg.zrwa, + cfg.select_all, cfg.timeout, NVME_ZNS_ZSA_OPEN, 0, NULL); + if (!err) + printf("zns-open-zone: Success zone slba:%"PRIx64" nsid:%d\n", + (uint64_t)cfg.zslba, cfg.namespace_id); + else + nvme_show_status(err); +close_fd: + close(fd); + return nvme_status_to_errno(err, false); } static int reset_zone(int argc, char **argv, struct command *cmd, struct plugin *plugin) @@ -484,6 +535,7 @@ static int set_zone_desc(int argc, char **argv, struct command *cmd, struct plug { const char *desc = "Set Zone Descriptor Extension\n"; const char *zslba = "starting LBA of the zone for this command"; + const char *zrwa = "Zone Random Write Area Allocation"; const char *data = "optional file for zone extention data (default stdin)"; const char *timeout = "timeout value, in milliseconds"; @@ -493,6 +545,7 @@ static int set_zone_desc(int argc, char **argv, struct command *cmd, struct plug struct config { __u64 zslba; + bool zrwa; __u32 namespace_id; char *file; __u32 timeout; @@ -503,6 +556,7 @@ static int set_zone_desc(int argc, char **argv, struct command *cmd, struct plug OPT_ARGS(opts) = { OPT_UINT("namespace-id", 'n', &cfg.namespace_id, namespace_id), OPT_SUFFIX("start-lba", 's', &cfg.zslba, zslba), + OPT_FLAG("zrwa", 'r', &cfg.zrwa, zrwa), OPT_FILE("data", 'd', &cfg.file, data), OPT_UINT("timeout", 't', &cfg.timeout, timeout), OPT_END() @@ -552,8 +606,8 @@ static int set_zone_desc(int argc, char **argv, struct command *cmd, struct plug goto close_ffd; } - err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zslba, 0, cfg.timeout, - NVME_ZNS_ZSA_SET_DESC_EXT, data_len, buf); + err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zslba, cfg.zrwa, 0, + cfg.timeout, NVME_ZNS_ZSA_SET_DESC_EXT, data_len, buf); if (!err) printf("set-zone-desc: Success, zone:%"PRIx64" nsid:%d\n", (uint64_t)cfg.zslba, cfg.namespace_id); @@ -571,6 +625,54 @@ close_fd: return nvme_status_to_errno(err, false); } + +static int flush_zone(int argc, char **argv, struct command *cmd, struct plugin *plugin) +{ + const char *desc = "Flush Explicit ZRWA Range"; + const char *zllba = "The last LBA of the zone to be flushed"; + const char *timeout = "timeout value, in milliseconds"; + + int err, fd; + + struct config { + __u64 zllba; + __u32 namespace_id; + __u32 timeout; + }; + + struct config cfg = {}; + + OPT_ARGS(opts) = { + OPT_UINT("namespace-id", 'n', &cfg.namespace_id, namespace_id), + OPT_SUFFIX("last-lba", 'l', &cfg.zllba, zllba), + OPT_UINT("timeout", 't', &cfg.timeout, timeout), + OPT_END() + }; + + fd = parse_and_open(argc, argv, desc, opts); + if (fd < 0) + return errno; + + if (!cfg.namespace_id) { + err = nvme_get_nsid(fd, &cfg.namespace_id); + if (err < 0) { + perror("get-namespace-id"); + goto close_fd; + } + } + + err = __zns_mgmt_send(fd, cfg.namespace_id, cfg.zllba, 0, 0, cfg.timeout, + NVME_ZNS_ZSA_ZRWA_FLUSH, 0, NULL); + if (!err) + printf("zns-flush-zone: Success, last lba:%"PRIx64" nsid:%d\n", + (uint64_t)cfg.zllba, cfg.namespace_id); + else + nvme_show_status(err); +close_fd: + close(fd); + return nvme_status_to_errno(err, false); +} + static int zone_mgmt_recv(int argc, char **argv, struct command *cmd, struct plugin *plugin) { const char *desc = "Zone Management Receive"; diff --git a/plugins/zns/zns.h b/plugins/zns/zns.h index 17011e1d..29af49b3 100644 --- a/plugins/zns/zns.h +++ b/plugins/zns/zns.h @@ -18,6 +18,7 @@ PLUGIN(NAME("zns", "Zoned Namespace Command Set", NVME_VERSION), ENTRY("open-zone", "Open one or more zones", open_zone) ENTRY("offline-zone", "Offline one or more zones", offline_zone) ENTRY("set-zone-desc", "Attach zone descriptor extension data to a zone", set_zone_desc) + ENTRY("flush-zone", "Flushes a range of logical blocks from a ZRWA to a zone.", flush_zone) ENTRY("changed-zone-list", "Retrieve the changed zone list log", changed_zone_list) ENTRY("zone-mgmt-recv", "Send the zone management receive command", zone_mgmt_recv) ENTRY("zone-mgmt-send", "Send the zone management send command", zone_mgmt_send)