get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

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

{
    "id": 139803,
    "url": "http://patches.dpdk.org/api/patches/139803/?format=api",
    "web_url": "http://patches.dpdk.org/project/dpdk/patch/20240502144149.66446-1-daniel.gregory@bytedance.com/",
    "project": {
        "id": 1,
        "url": "http://patches.dpdk.org/api/projects/1/?format=api",
        "name": "DPDK",
        "link_name": "dpdk",
        "list_id": "dev.dpdk.org",
        "list_email": "dev@dpdk.org",
        "web_url": "http://core.dpdk.org",
        "scm_url": "git://dpdk.org/dpdk",
        "webscm_url": "http://git.dpdk.org/dpdk",
        "list_archive_url": "https://inbox.dpdk.org/dev",
        "list_archive_url_format": "https://inbox.dpdk.org/dev/{}",
        "commit_url_format": ""
    },
    "msgid": "<20240502144149.66446-1-daniel.gregory@bytedance.com>",
    "list_archive_url": "https://inbox.dpdk.org/dev/20240502144149.66446-1-daniel.gregory@bytedance.com",
    "date": "2024-05-02T14:41:50",
    "name": "[RFC] eal/riscv: add support for zawrs extension",
    "commit_ref": null,
    "pull_url": null,
    "state": "new",
    "archived": false,
    "hash": "765221c34c789f7481a94392a5a2e4b1d2f54d17",
    "submitter": {
        "id": 3322,
        "url": "http://patches.dpdk.org/api/people/3322/?format=api",
        "name": "Daniel Gregory",
        "email": "daniel.gregory@bytedance.com"
    },
    "delegate": {
        "id": 1,
        "url": "http://patches.dpdk.org/api/users/1/?format=api",
        "username": "tmonjalo",
        "first_name": "Thomas",
        "last_name": "Monjalon",
        "email": "thomas@monjalon.net"
    },
    "mbox": "http://patches.dpdk.org/project/dpdk/patch/20240502144149.66446-1-daniel.gregory@bytedance.com/mbox/",
    "series": [
        {
            "id": 31866,
            "url": "http://patches.dpdk.org/api/series/31866/?format=api",
            "web_url": "http://patches.dpdk.org/project/dpdk/list/?series=31866",
            "date": "2024-05-02T14:41:50",
            "name": "[RFC] eal/riscv: add support for zawrs extension",
            "version": 1,
            "mbox": "http://patches.dpdk.org/series/31866/mbox/"
        }
    ],
    "comments": "http://patches.dpdk.org/api/patches/139803/comments/",
    "check": "warning",
    "checks": "http://patches.dpdk.org/api/patches/139803/checks/",
    "tags": {},
    "related": [],
    "headers": {
        "Return-Path": "<dev-bounces@dpdk.org>",
        "X-Original-To": "patchwork@inbox.dpdk.org",
        "Delivered-To": "patchwork@inbox.dpdk.org",
        "Received": [
            "from mails.dpdk.org (mails.dpdk.org [217.70.189.124])\n\tby inbox.dpdk.org (Postfix) with ESMTP id A681F43F69;\n\tThu,  2 May 2024 16:44:51 +0200 (CEST)",
            "from mails.dpdk.org (localhost [127.0.0.1])\n\tby mails.dpdk.org (Postfix) with ESMTP id 69EFE402B2;\n\tThu,  2 May 2024 16:44:51 +0200 (CEST)",
            "from mail-wm1-f42.google.com (mail-wm1-f42.google.com\n [209.85.128.42]) by mails.dpdk.org (Postfix) with ESMTP id C30EC40299\n for <dev@dpdk.org>; Thu,  2 May 2024 16:44:49 +0200 (CEST)",
            "by mail-wm1-f42.google.com with SMTP id\n 5b1f17b1804b1-41ba1ba55ffso11641375e9.1\n for <dev@dpdk.org>; Thu, 02 May 2024 07:44:49 -0700 (PDT)",
            "from C02FF2N1MD6T.bytedance.net ([79.173.157.19])\n by smtp.gmail.com with ESMTPSA id\n u17-20020a05600c19d100b004186eb69a55sm2185062wmq.25.2024.05.02.07.44.48\n (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);\n Thu, 02 May 2024 07:44:48 -0700 (PDT)"
        ],
        "DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/relaxed;\n d=bytedance.com; s=google; t=1714661089; x=1715265889; darn=dpdk.org;\n h=content-transfer-encoding:mime-version:message-id:date:subject:cc\n :to:from:from:to:cc:subject:date:message-id:reply-to;\n bh=Xi5qeL1//36OXBpVb9kJN6nJwKIDmbwjWb4jYwqpcCU=;\n b=kH1kg8OwovX5d1qw8kO/4s8WSrmABjLz9cjfSE/SiLQq9ihF5AUEIkShOxHCm3d4bm\n BONs+egD3MHJ4lWA0m0KJmKNGAwDBvXBy1lR1ksY/aRoAI5UaBSWW43maK9wlC/SYgmh\n UVwAUlQuk4lRORH8ot5JS3fs4XnJBjxmvxjFdpGBOijB1Mhnr7NWNilb4uwKvTChtNjq\n nJCG1CTxBCIMWA/1A3coT29caN1QKQtW1H+n0Wu4gkHLhtKis5u/DIQPzKLWPyXhpABV\n hd7pkuSZa/74puE51IaMQnlQV8DHiIYpN0I/+r9YZL4u2zHhY1Xba9OqpfU6oe2dmmPI\n 846A==",
        "X-Google-DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/relaxed;\n d=1e100.net; s=20230601; t=1714661089; x=1715265889;\n h=content-transfer-encoding:mime-version:message-id:date:subject:cc\n :to:from:x-gm-message-state:from:to:cc:subject:date:message-id\n :reply-to;\n bh=Xi5qeL1//36OXBpVb9kJN6nJwKIDmbwjWb4jYwqpcCU=;\n b=hSCe4uQqNMuf6NhQwVARPnnMgy9TcpMDCgcu3Anaqv1EkprkPeOF8lepbeSNxzLNgj\n +X/zQcaPXJiXSIMKezB38ZFPbsHrbFnBaygq1AB0o83YdpAsGORVz94FAL+CdwEw8jcF\n o1gOW/bVUxq98s5ToqNImeXJPJ7f/wLE3enIteri7c6+yaI3bVgbXD7EOWcJcggmYicN\n s8TnfbFxykA3KYkmSU+ZkBEUmr7nlpqmL0+f3ni5+KcEuWZqji7apMgBMjqe0zZBgqKm\n j6vYRNkVSFFmXVGEz5wsebEs6jGA8e7nT/soC6FKQpMSFHhuP7XhkG5ZaXl+0Za/uLJo\n VkdQ==",
        "X-Gm-Message-State": "AOJu0YwpzDVjyqxVe+PtpgoVl8WDa8ij5TNKTcKwr7LIN5DoUYTsZEzv\n LrijjyB7YAj2OW9fsnOVQfGGiUqjqggwTuh76/T2uxBTxfBVdW4pquWbd2gXP8c=",
        "X-Google-Smtp-Source": "\n AGHT+IECTNaRMNy1peTTL59zRVWhqYWOVqyPRTpC6bAcq1hq20PHEOV0gdysfHI17AG2U4A9cwpjog==",
        "X-Received": "by 2002:a05:600c:3b8f:b0:41c:13f6:1ee1 with SMTP id\n n15-20020a05600c3b8f00b0041c13f61ee1mr2634764wms.4.1714661089253;\n Thu, 02 May 2024 07:44:49 -0700 (PDT)",
        "From": "Daniel Gregory <daniel.gregory@bytedance.com>",
        "To": "Stanislaw Kardach <stanislaw.kardach@gmail.com>,\n Bruce Richardson <bruce.richardson@intel.com>",
        "Cc": "dev@dpdk.org, Liang Ma <liangma@bytedance.com>,\n Daniel Gregory <daniel.gregory@bytedance.com>,\n Punit Agrawal <punit.agrawal@bytedance.com>",
        "Subject": "[RFC PATCH] eal/riscv: add support for zawrs extension",
        "Date": "Thu,  2 May 2024 15:41:50 +0100",
        "Message-Id": "<20240502144149.66446-1-daniel.gregory@bytedance.com>",
        "X-Mailer": "git-send-email 2.39.3 (Apple Git-146)",
        "MIME-Version": "1.0",
        "Content-Transfer-Encoding": "8bit",
        "X-BeenThere": "dev@dpdk.org",
        "X-Mailman-Version": "2.1.29",
        "Precedence": "list",
        "List-Id": "DPDK patches and discussions <dev.dpdk.org>",
        "List-Unsubscribe": "<https://mails.dpdk.org/options/dev>,\n <mailto:dev-request@dpdk.org?subject=unsubscribe>",
        "List-Archive": "<http://mails.dpdk.org/archives/dev/>",
        "List-Post": "<mailto:dev@dpdk.org>",
        "List-Help": "<mailto:dev-request@dpdk.org?subject=help>",
        "List-Subscribe": "<https://mails.dpdk.org/listinfo/dev>,\n <mailto:dev-request@dpdk.org?subject=subscribe>",
        "Errors-To": "dev-bounces@dpdk.org"
    },
    "content": "The zawrs extension adds a pair of instructions that stall a core until\na memory location is written to. This patch uses one of them to\nimplement RISCV-specific versions of the rte_wait_until_equal_*\nfunctions. This is potentially more energy efficient than the default\nimplementation that uses rte_pause/Zihintpause.\n\nThe technique works as follows:\n\n* Create a reservation set containing the address we want to wait on\n  using an atomic load (lr.dw)\n* Call wrs.nto - this blocks until the reservation set is invalidated by\n  someone else writing to that address\n* Execution can also resume arbitrarily, so we still need to check\n  whether a change occurred and loop if not\n\nDue to RISC-V atomics only supporting naturally aligned word (32 bit)\nand double word (64 bit) loads, I've used pointer rounding and bit\nshifting to implement waiting on 16-bit values.\n\nThis new functionality is controlled by a Meson flag that is disabled by\ndefault.\n\nSigned-off-by: Daniel Gregory <daniel.gregory@bytedance.com>\nSuggested-by: Punit Agrawal <punit.agrawal@bytedance.com>\n---\n\nPosting as an RFC to get early feedback and enable testing by others\nwith Zawrs-enabled hardware. Whilst I have been able to test it compiles\n& passes tests using QEMU, I am waiting on some Zawrs-enabled hardware\nto become available before I carry out performance tests.\n\nNonetheless, I would be glad to hear any feedback on the general\napproach. Thanks, Daniel\n\n config/riscv/meson.build          |   5 ++\n lib/eal/riscv/include/rte_pause.h | 139 ++++++++++++++++++++++++++++++\n 2 files changed, 144 insertions(+)",
    "diff": "diff --git a/config/riscv/meson.build b/config/riscv/meson.build\nindex 07d7d9da23..4cfdc42ecb 100644\n--- a/config/riscv/meson.build\n+++ b/config/riscv/meson.build\n@@ -26,6 +26,11 @@ flags_common = [\n     # read from /proc/device-tree/cpus/timebase-frequency. This property is\n     # guaranteed on Linux, as riscv time_init() requires it.\n     ['RTE_RISCV_TIME_FREQ', 0],\n+\n+    # Enable use of RISC-V Wait-on-Reservation-Set extension (Zawrs)\n+    # Mitigates looping when polling on memory locations\n+    # Make sure to add '_zawrs' to your target's -march below\n+    ['RTE_RISCV_ZAWRS', false]\n ]\n \n ## SoC-specific options.\ndiff --git a/lib/eal/riscv/include/rte_pause.h b/lib/eal/riscv/include/rte_pause.h\nindex cb8e9ca52d..e7b43dffa3 100644\n--- a/lib/eal/riscv/include/rte_pause.h\n+++ b/lib/eal/riscv/include/rte_pause.h\n@@ -11,6 +11,12 @@\n extern \"C\" {\n #endif\n \n+#ifdef RTE_RISCV_ZAWRS\n+#define RTE_WAIT_UNTIL_EQUAL_ARCH_DEFINED\n+#endif\n+\n+#include <rte_debug.h>\n+\n #include \"rte_atomic.h\"\n \n #include \"generic/rte_pause.h\"\n@@ -24,6 +30,139 @@ static inline void rte_pause(void)\n \tasm volatile(\".int 0x0100000F\" : : : \"memory\");\n }\n \n+#ifdef RTE_RISCV_ZAWRS\n+\n+/*\n+ * Atomic load from an address, it returns either a sign-extended word or\n+ * doubleword and creates a 'reservation set' containing the read memory\n+ * location. When someone else writes to the reservation set, it is invalidated,\n+ * causing any stalled WRS instructions to resume.\n+ *\n+ * Address needs to be naturally aligned.\n+ */\n+#define __RTE_RISCV_LR_32(src, dst, memorder) do {                \\\n+\tif ((memorder) == rte_memory_order_relaxed) {             \\\n+\t\tasm volatile(\"lr.w %0, (%1)\"                      \\\n+\t\t\t\t: \"=r\" (dst)                      \\\n+\t\t\t\t: \"r\" (src)                       \\\n+\t\t\t\t: \"memory\");                      \\\n+\t} else {                                                  \\\n+\t\tasm volatile(\"lr.w.aq %0, (%1)\"                   \\\n+\t\t\t\t: \"=r\" (dst)                      \\\n+\t\t\t\t: \"r\" (src)                       \\\n+\t\t\t\t: \"memory\");                      \\\n+\t} } while (0)\n+#define __RTE_RISCV_LR_64(src, dst, memorder) do {                \\\n+\tif ((memorder) == rte_memory_order_relaxed) {             \\\n+\t\tasm volatile(\"lr.d %0, (%1)\"                      \\\n+\t\t\t\t: \"=r\" (dst)                      \\\n+\t\t\t\t: \"r\" (src)                       \\\n+\t\t\t\t: \"memory\");                      \\\n+\t} else {                                                  \\\n+\t\tasm volatile(\"lr.d.aq %0, (%1)\"                   \\\n+\t\t\t\t: \"=r\" (dst)                      \\\n+\t\t\t\t: \"r\" (src)                       \\\n+\t\t\t\t: \"memory\");                      \\\n+\t} } while (0)\n+\n+/*\n+ * There's not a RISC-V atomic load primitive for halfwords, so cast up to a\n+ * _naturally aligned_ word and extract the halfword we want\n+ */\n+#define __RTE_RISCV_LR_16(src, dst, memorder) do {                      \\\n+\tuint32_t word;                                                  \\\n+\t__RTE_RISCV_LR_32(((uintptr_t)(src) & (~3)), word, (memorder)); \\\n+\tif ((size_t)(src) & 3)                                          \\\n+\t\t(dst) = (typeof(dst))(word >> 16);                      \\\n+\telse                                                            \\\n+\t\t(dst) = (typeof(dst))(word & 0xFFFF);                   \\\n+} while (0)\n+\n+#define __RTE_RISCV_LR(src, dst, memorder, size) {                \\\n+\tRTE_BUILD_BUG_ON(size != 16 && size != 32 && size != 64); \\\n+\tif (size == 16)                                           \\\n+\t\t__RTE_RISCV_LR_16(src, dst, memorder);            \\\n+\telse if (size == 32)                                      \\\n+\t\t__RTE_RISCV_LR_32(src, dst, memorder);            \\\n+\telse if (size == 64)                                      \\\n+\t\t__RTE_RISCV_LR_64(src, dst, memorder);            \\\n+}\n+\n+/*\n+ * Wait-on-Reservation-Set extension instruction, it stalls execution until the\n+ * reservation set is invalidated or an interrupt is observed.\n+ * A loop is likely still needed as it may stop stalling arbitrarily.\n+ */\n+#define __RTE_RISCV_WRS_NTO() { asm volatile(\"wrs.nto\" : : : \"memory\"); }\n+\n+static __rte_always_inline void\n+rte_wait_until_equal_16(volatile uint16_t *addr, uint16_t expected,\n+\t\tint memorder)\n+{\n+\tuint16_t value;\n+\n+\tRTE_ASSERT(memorder == rte_memory_order_acquire ||\n+\t\tmemorder == rte_memory_order_relaxed);\n+\tRTE_ASSERT(((size_t)addr & 1) == 0);\n+\n+\t__RTE_RISCV_LR_16(addr, value, memorder);\n+\twhile (value != expected) {\n+\t\t__RTE_RISCV_WRS_NTO();\n+\t\t__RTE_RISCV_LR_16(addr, value, memorder);\n+\t}\n+}\n+\n+static __rte_always_inline void\n+rte_wait_until_equal_32(volatile uint32_t *addr, uint32_t expected,\n+\t\tint memorder)\n+{\n+\tuint32_t value;\n+\n+\tRTE_ASSERT(memorder == rte_memory_order_acquire ||\n+\t\tmemorder == rte_memory_order_relaxed);\n+\tRTE_ASSERT(((size_t)addr & 3) == 0);\n+\n+\t__RTE_RISCV_LR_32(addr, value, memorder);\n+\twhile (value != expected) {\n+\t\t__RTE_RISCV_WRS_NTO();\n+\t\t__RTE_RISCV_LR_32(addr, value, memorder);\n+\t}\n+}\n+\n+static __rte_always_inline void\n+rte_wait_until_equal_64(volatile uint64_t *addr, uint64_t expected,\n+\t\tint memorder)\n+{\n+\tuint64_t value;\n+\n+\tRTE_ASSERT(memorder == rte_memory_order_acquire ||\n+\t\tmemorder == rte_memory_order_relaxed);\n+\tRTE_ASSERT(((size_t)addr & 7) == 0);\n+\n+\t__RTE_RISCV_LR_64(addr, value, memorder);\n+\twhile (value != expected) {\n+\t\t__RTE_RISCV_WRS_NTO();\n+\t\t__RTE_RISCV_LR_64(addr, value, memorder);\n+\t}\n+}\n+\n+#define RTE_WAIT_UNTIL_MASKED(addr, mask, cond, expected, memorder) do { \\\n+\tRTE_BUILD_BUG_ON(!__builtin_constant_p(memorder));               \\\n+\tRTE_BUILD_BUG_ON(memorder != rte_memory_order_acquire &&         \\\n+\t\tmemorder != rte_memory_order_relaxed);                   \\\n+\tRTE_ASSERT(((size_t)(addr) & (sizeof(*(addr)) - 1)) != 0);       \\\n+\tconst uint32_t size = sizeof(*(addr)) << 3;                      \\\n+\ttypeof(*(addr)) expected_value = (expected);                     \\\n+\ttypeof(*(addr)) value;                                           \\\n+\t__RTE_RISCV_LR((addr), value, memorder, size);                   \\\n+\twhile (!((value & (mask)) cond expected_value)) {                \\\n+\t\t__RTE_RISCV_WRS_NTO();                                   \\\n+\t\t__RTE_RISCV_LR((addr), value, memorder, size);           \\\n+\t}                                                                \\\n+} while (0)\n+\n+#endif /* RTE_RISCV_ZAWRS */\n+\n #ifdef __cplusplus\n }\n #endif\n",
    "prefixes": [
        "RFC"
    ]
}