get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

GET /api/1.2/patches/2224425/?format=api
HTTP 200 OK
Allow: GET, PUT, PATCH, HEAD, OPTIONS
Content-Type: application/json
Vary: Accept

{
    "id": 2224425,
    "url": "http://patchwork.ozlabs.org/api/1.2/patches/2224425/?format=api",
    "web_url": "http://patchwork.ozlabs.org/project/uboot/patch/20260417120319.573470-1-christian.poetzsch@kernkonzept.com/",
    "project": {
        "id": 18,
        "url": "http://patchwork.ozlabs.org/api/1.2/projects/18/?format=api",
        "name": "U-Boot",
        "link_name": "uboot",
        "list_id": "u-boot.lists.denx.de",
        "list_email": "u-boot@lists.denx.de",
        "web_url": null,
        "scm_url": null,
        "webscm_url": null,
        "list_archive_url": "",
        "list_archive_url_format": "",
        "commit_url_format": ""
    },
    "msgid": "<20260417120319.573470-1-christian.poetzsch@kernkonzept.com>",
    "list_archive_url": null,
    "date": "2026-04-17T12:03:19",
    "name": "[v2] virtio: add support for SIZE_MAX & SEG_MAX features",
    "commit_ref": null,
    "pull_url": null,
    "state": "new",
    "archived": false,
    "hash": "0c0808b294b24e17448cfbb46a956e35b7e6bf9e",
    "submitter": {
        "id": 88226,
        "url": "http://patchwork.ozlabs.org/api/1.2/people/88226/?format=api",
        "name": "Christian Pötzsch",
        "email": "christian.poetzsch@kernkonzept.com"
    },
    "delegate": {
        "id": 3651,
        "url": "http://patchwork.ozlabs.org/api/1.2/users/3651/?format=api",
        "username": "trini",
        "first_name": "Tom",
        "last_name": "Rini",
        "email": "trini@ti.com"
    },
    "mbox": "http://patchwork.ozlabs.org/project/uboot/patch/20260417120319.573470-1-christian.poetzsch@kernkonzept.com/mbox/",
    "series": [
        {
            "id": 500315,
            "url": "http://patchwork.ozlabs.org/api/1.2/series/500315/?format=api",
            "web_url": "http://patchwork.ozlabs.org/project/uboot/list/?series=500315",
            "date": "2026-04-17T12:03:19",
            "name": "[v2] virtio: add support for SIZE_MAX & SEG_MAX features",
            "version": 2,
            "mbox": "http://patchwork.ozlabs.org/series/500315/mbox/"
        }
    ],
    "comments": "http://patchwork.ozlabs.org/api/patches/2224425/comments/",
    "check": "pending",
    "checks": "http://patchwork.ozlabs.org/api/patches/2224425/checks/",
    "tags": {},
    "related": [],
    "headers": {
        "Return-Path": "<u-boot-bounces@lists.denx.de>",
        "X-Original-To": "incoming@patchwork.ozlabs.org",
        "Delivered-To": "patchwork-incoming@legolas.ozlabs.org",
        "Authentication-Results": [
            "legolas.ozlabs.org;\n\tdkim=pass (2048-bit key;\n unprotected) header.d=kernkonzept.com header.i=@kernkonzept.com\n header.a=rsa-sha256 header.s=mx1 header.b=a4KBks4S;\n\tdkim-atps=neutral",
            "legolas.ozlabs.org;\n spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de\n (client-ip=2a01:238:438b:c500:173d:9f52:ddab:ee01; helo=phobos.denx.de;\n envelope-from=u-boot-bounces@lists.denx.de; receiver=patchwork.ozlabs.org)",
            "phobos.denx.de;\n dmarc=pass (p=none dis=none) header.from=kernkonzept.com",
            "phobos.denx.de;\n spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de",
            "phobos.denx.de;\n\tdkim=pass (2048-bit key;\n unprotected) header.d=kernkonzept.com header.i=@kernkonzept.com\n header.b=\"a4KBks4S\";\n\tdkim-atps=neutral",
            "phobos.denx.de; dmarc=pass (p=none dis=none)\n header.from=kernkonzept.com",
            "phobos.denx.de; spf=pass\n smtp.mailfrom=christian.poetzsch@kernkonzept.com"
        ],
        "Received": [
            "from phobos.denx.de (phobos.denx.de\n [IPv6:2a01:238:438b:c500:173d:9f52:ddab:ee01])\n\t(using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)\n\t key-exchange x25519 server-signature ECDSA (secp384r1) server-digest SHA384)\n\t(No client certificate requested)\n\tby legolas.ozlabs.org (Postfix) with ESMTPS id 4fxtpM0SdMz1yHp\n\tfor <incoming@patchwork.ozlabs.org>; Fri, 17 Apr 2026 22:04:10 +1000 (AEST)",
            "from h2850616.stratoserver.net (localhost [IPv6:::1])\n\tby phobos.denx.de (Postfix) with ESMTP id E907683EEF;\n\tFri, 17 Apr 2026 14:04:01 +0200 (CEST)",
            "by phobos.denx.de (Postfix, from userid 109)\n id C4C9483FC0; Fri, 17 Apr 2026 14:04:00 +0200 (CEST)",
            "from mx.kernkonzept.com (serv1.kernkonzept.com\n [IPv6:2a01:4f8:1c1c:b490::2])\n (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits))\n (No client certificate requested)\n by phobos.denx.de (Postfix) with ESMTPS id AAE5283B99\n for <u-boot@lists.denx.de>; Fri, 17 Apr 2026 14:03:58 +0200 (CEST)",
            "from [10.22.3.25] (helo=serv2.dd1.int.kernkonzept.com.)\n by mx.kernkonzept.com with esmtpsa\n (TLS1.3:ECDHE_X25519__RSA_PSS_RSAE_SHA256__AES_256_GCM:256) (Exim 4.98.2)\n id 1wDhvR-0000000GURC-0gdL; Fri, 17 Apr 2026 14:03:57 +0200"
        ],
        "X-Spam-Checker-Version": "SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de",
        "X-Spam-Level": "",
        "X-Spam-Status": "No, score=-2.1 required=5.0 tests=BAYES_00,DKIM_SIGNED,\n DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,RCVD_IN_DNSWL_BLOCKED,\n SPF_HELO_NONE,SPF_PASS autolearn=ham autolearn_force=no version=3.4.2",
        "DKIM-Signature": "v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed;\n d=kernkonzept.com; s=mx1; h=Content-Transfer-Encoding:Content-Type:\n MIME-Version:References:In-Reply-To:Message-ID:Date:Subject:Cc:To:From:\n Reply-To:Content-ID:Content-Description;\n bh=A6n45Ge/nKG+XErWbL/e02G1RkfkovF2SkFVBNVuZpY=; b=a4KBks4SaP5SN3esfTQDXFiOrB\n eEYMcaK7PF3GCfZPo7Nb12WThdYOKPVUv8smFcHkZ9xbtre950iXfmAz0cMwOBCMednDIOWA3T+Ug\n hN5D1HcWlTcojlWdafvHp5aTLnhIOfMhfuUHDTxQblN9ePvdh6FUCDi1NBrg/11uKKk189n/8e3EE\n E8Ks+7lR/GfzHMTLtLwGnHVzqcKWNy1PRlG8G6W9tLvI5PTwkJgloJxbq5EEyQ+YuKVrd5MAg5HQO\n vvslPoaF0PY578wgYRTS6FHplo/Xtg6EhOJcrHJWSlLMFnA29Ecjx9SCl4gMNVNjsfbHO4f0PlwGw\n pMaSkvcA==;",
        "From": "=?utf-8?q?Christian_P=C3=B6tzsch?= <christian.poetzsch@kernkonzept.com>",
        "To": "u-boot@lists.denx.de",
        "Cc": "Bin Meng <bmeng.cn@gmail.com>, Tom Rini <trini@konsulko.com>,\n Simon Glass <sjg@chromium.org>,\n =?utf-8?q?Christian_P=C3=B6tzsch?= <christian.poetzsch@kernkonzept.com>,\n Adam Lackorzynski <adam@l4re.org>",
        "Subject": "[PATCH v2] virtio: add support for SIZE_MAX & SEG_MAX features",
        "Date": "Fri, 17 Apr 2026 14:03:19 +0200",
        "Message-ID": "<20260417120319.573470-1-christian.poetzsch@kernkonzept.com>",
        "X-Mailer": "git-send-email 2.47.3",
        "In-Reply-To": "<20260327081858.311591-1-christian.poetzsch@kernkonzept.com>",
        "References": "<20260327081858.311591-1-christian.poetzsch@kernkonzept.com>",
        "MIME-Version": "1.0",
        "Content-Type": "text/plain; charset=UTF-8",
        "Content-Transfer-Encoding": "8bit",
        "X-BeenThere": "u-boot@lists.denx.de",
        "X-Mailman-Version": "2.1.39",
        "Precedence": "list",
        "List-Id": "U-Boot discussion <u-boot.lists.denx.de>",
        "List-Unsubscribe": "<https://lists.denx.de/options/u-boot>,\n <mailto:u-boot-request@lists.denx.de?subject=unsubscribe>",
        "List-Archive": "<https://lists.denx.de/pipermail/u-boot/>",
        "List-Post": "<mailto:u-boot@lists.denx.de>",
        "List-Help": "<mailto:u-boot-request@lists.denx.de?subject=help>",
        "List-Subscribe": "<https://lists.denx.de/listinfo/u-boot>,\n <mailto:u-boot-request@lists.denx.de?subject=subscribe>",
        "Errors-To": "u-boot-bounces@lists.denx.de",
        "Sender": "\"U-Boot\" <u-boot-bounces@lists.denx.de>",
        "X-Virus-Scanned": "clamav-milter 0.103.8 at phobos.denx.de",
        "X-Virus-Status": "Clean"
    },
    "content": "Some virtio implementations may forward the virtio requests directly to\nthe underlying hw. The hw may have some restrictions in how many and how\nbig the requests can be. Therefore, the corresponding virtio device will\nannounce this limitations with the SIZE_MAX & SEG_MAX feature.\n\nAdd support for those features. Split an io request into multiple virtio\nrequests if more than seg_max segments would be used. Also split a\nsingle buffer request into multiple segments if the buffer is bigger\nthen size_max.\n\nSigned-off-by: Christian Pötzsch <christian.poetzsch@kernkonzept.com>\nSigned-off-by: Adam Lackorzynski <adam@l4re.org>\n---\nChanges in v2:\n- Fixed behavior in error case in virtio_blk_do_req\n- Fixed return check in virtio_blk_do_single_req\n- Change comment style\n\n drivers/virtio/virtio_blk.c | 122 +++++++++++++++++++++++++++++-------\n 1 file changed, 99 insertions(+), 23 deletions(-)",
    "diff": "diff --git a/drivers/virtio/virtio_blk.c b/drivers/virtio/virtio_blk.c\nindex 3dd0cf36268..45fb596a330 100644\n--- a/drivers/virtio/virtio_blk.c\n+++ b/drivers/virtio/virtio_blk.c\n@@ -14,6 +14,7 @@\n #include <virtio_ring.h>\n #include <linux/log2.h>\n #include \"virtio_blk.h\"\n+#include <malloc.h>\n \n /**\n  * struct virtio_blk_priv - private data for virtio block device\n@@ -23,10 +24,16 @@ struct virtio_blk_priv {\n \tstruct virtqueue *vq;\n \t/** @blksz_shift - log2 of block size divided by 512 */\n \tu32 blksz_shift;\n+\t/** @size_max - maximum segment size */\n+\tu32 size_max;\n+\t/** @seg_max - maximum segment count */\n+\tu32 seg_max;\n };\n \n static const u32 feature[] = {\n \tVIRTIO_BLK_F_BLK_SIZE,\n+\tVIRTIO_BLK_F_SIZE_MAX,\n+\tVIRTIO_BLK_F_SEG_MAX,\n \tVIRTIO_BLK_F_WRITE_ZEROES\n };\n \n@@ -67,50 +74,77 @@ static void virtio_blk_init_data_sg(void *buffer, lbaint_t blkcnt, struct virtio\n \tsg->length = blkcnt * 512;\n }\n \n-static ulong virtio_blk_do_req(struct udevice *dev, u64 sector,\n-\t\t\t       lbaint_t blkcnt, void *buffer, u32 type)\n+/*\n+ * Create, execute and wait for one single virtio request. On success the\n+ * transferred block count is returned and in the error case -EIO.\n+ */\n+static ulong virtio_blk_do_single_req(struct udevice *dev, u64 sector,\n+\t\t\t\t      lbaint_t blkcnt, char *buffer, u32 type)\n {\n \tstruct virtio_blk_priv *priv = dev_get_priv(dev);\n+\t/*\n+\t* The virtio device may have constrains on the maximum segment size.\n+\t* Calculate how many segments we need.\n+\t*/\n+\tu32 seg_cnt = (blkcnt * 512) / priv->size_max + 1;\n+\tlbaint_t seg_sec_cnt = priv->size_max / 512;\n \tstruct virtio_blk_outhdr out_hdr;\n \tstruct virtio_blk_discard_write_zeroes wz_hdr;\n \tunsigned int num_out = 0, num_in = 0;\n-\tstruct virtio_sg hdr_sg, wz_sg, data_sg, status_sg;\n-\tstruct virtio_sg *sgs[3];\n-\tu8 status;\n+\tstruct virtio_sg **sgs;\n+\tu8 status = VIRTIO_BLK_S_IOERR;\n \tint ret;\n+\tu32 i;\n \n-\tsector <<= priv->blksz_shift;\n-\tblkcnt <<= priv->blksz_shift;\n-\tvirtio_blk_init_header_sg(dev, sector, type, &out_hdr, &hdr_sg);\n-\tsgs[num_out++] = &hdr_sg;\n+\t/*\n+\t* +2 is header and status descriptor; seg_cnt is the number of data segments\n+\t* required. Needs to be dynamically allocated.\n+\t*/\n+\tsgs = calloc(seg_cnt + 2, sizeof(struct virtio_sg *));\n+\tif (!sgs)\n+\t\treturn -ENOMEM;\n+\n+\tfor (i = 0; i < seg_cnt + 2; ++i) {\n+\t\tsgs[i] = malloc(sizeof(struct virtio_sg));\n+\t\tif (!sgs[i])\n+\t\t\tgoto err_free;\n+\t}\n+\n+\tvirtio_blk_init_header_sg(dev, sector, type, &out_hdr, sgs[num_out++]);\n \n \tswitch (type) {\n \tcase VIRTIO_BLK_T_IN:\n-\tcase VIRTIO_BLK_T_OUT:\n-\t\tvirtio_blk_init_data_sg(buffer, blkcnt, &data_sg);\n-\t\tif (type & VIRTIO_BLK_T_OUT)\n-\t\t\tsgs[num_out++] = &data_sg;\n-\t\telse\n-\t\t\tsgs[num_out + num_in++] = &data_sg;\n+\tcase VIRTIO_BLK_T_OUT: {\n+\t\ti = 0;\n+\t\twhile (i < blkcnt) {\n+\t\t\tu32 blk_per_seg = min(blkcnt - i, seg_sec_cnt);\n+\n+\t\t\tif (type & VIRTIO_BLK_T_OUT)\n+\t\t\t\tvirtio_blk_init_data_sg(buffer + i * 512, blk_per_seg,\n+\t\t\t\t\t\t\tsgs[num_out++]);\n+\t\t\telse\n+\t\t\t\tvirtio_blk_init_data_sg(buffer + i * 512, blk_per_seg,\n+\t\t\t\t\t\t\tsgs[num_out + num_in++]);\n+\t\t\ti += blk_per_seg;\n+\t\t}\n \t\tbreak;\n-\n+\t}\n \tcase VIRTIO_BLK_T_WRITE_ZEROES:\n-\t\tvirtio_blk_init_write_zeroes_sg(dev, sector, blkcnt, &wz_hdr, &wz_sg);\n-\t\tsgs[num_out++] = &wz_sg;\n+\t\tvirtio_blk_init_write_zeroes_sg(dev, sector, blkcnt, &wz_hdr,\n+\t\t\t\t\t\tsgs[num_out++]);\n \t\tbreak;\n \n \tdefault:\n-\t\treturn -EINVAL;\n+\t\tgoto err_free;\n \t}\n \n-\tvirtio_blk_init_status_sg(&status, &status_sg);\n-\tsgs[num_out + num_in++] = &status_sg;\n+\tvirtio_blk_init_status_sg(&status, sgs[num_out + num_in++]);\n \tlog_debug(\"dev=%s, active=%d, priv=%p, priv->vq=%p\\n\", dev->name,\n \t\t  device_active(dev), priv, priv->vq);\n \n \tret = virtqueue_add(priv->vq, sgs, num_out, num_in);\n \tif (ret)\n-\t\treturn ret;\n+\t\tgoto err_free;\n \n \tvirtqueue_kick(priv->vq);\n \n@@ -119,7 +153,40 @@ static ulong virtio_blk_do_req(struct udevice *dev, u64 sector,\n \t\t;\n \tlog_debug(\"done\\n\");\n \n-\treturn status == VIRTIO_BLK_S_OK ? blkcnt >> priv->blksz_shift : -EIO;\n+err_free:\n+\tfor (i = 0; i < seg_cnt + 2; ++i)\n+\t\tfree(sgs[i]);\n+\tfree(sgs);\n+\n+\treturn status == VIRTIO_BLK_S_OK ? blkcnt : -EIO;\n+}\n+\n+static ulong virtio_blk_do_req(struct udevice *dev, u64 sector,\n+\t\t\t       lbaint_t blkcnt, char *buffer, u32 type)\n+{\n+\tstruct virtio_blk_priv *priv = dev_get_priv(dev);\n+\tlbaint_t seg_sec_cnt = priv->size_max / 512;\n+\tu32 i = 0;\n+\tulong ret;\n+\n+\tsector <<= priv->blksz_shift;\n+\tblkcnt <<= priv->blksz_shift;\n+\n+\t/*\n+\t* The virtio device may have constrains on the maximum segment count. So\n+\t* send multiple virtio requests one after each other, if so.\n+\t*/\n+\twhile (i < blkcnt) {\n+\t\tu32 blk_per_sg = min(blkcnt - i, seg_sec_cnt * priv->seg_max);\n+\n+\t\tret = virtio_blk_do_single_req(dev, sector + i, blk_per_sg,\n+\t\t\t\t\t       buffer + i * 512, type);\n+\t\tif (ret < 0)\n+\t\t\treturn ret;\n+\t\ti += blk_per_sg;\n+\t}\n+\n+\treturn blkcnt >> priv->blksz_shift;\n }\n \n static ulong virtio_blk_read(struct udevice *dev, lbaint_t start,\n@@ -207,6 +274,15 @@ static int virtio_blk_probe(struct udevice *dev)\n \tpriv->blksz_shift = desc->log2blksz - 9;\n \tdesc->lba >>= priv->blksz_shift;\n \n+\tif (virtio_has_feature(dev, VIRTIO_BLK_F_SIZE_MAX))\n+\t\tvirtio_cread(dev, struct virtio_blk_config, size_max, &priv->size_max);\n+\telse\n+\t\tpriv->size_max = -1U;\n+\tif (virtio_has_feature(dev, VIRTIO_BLK_F_SEG_MAX))\n+\t\tvirtio_cread(dev, struct virtio_blk_config, seg_max, &priv->seg_max);\n+\telse\n+\t\tpriv->seg_max = -1U;\n+\n \treturn 0;\n }\n \n",
    "prefixes": [
        "v2"
    ]
}