From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail.openvz.org (mail.openvz.org [69.168.225.77]) by lore.virtuozzo.com (Postfix) with ESMTPS id DFF9481377 for ; Fri, 6 Nov 2026 14:03:17 +0000 (UTC) Received: from mail.openvz.org (localhost [127.0.0.1]) by mail.openvz.org (8.14.4/8.14.4) with ESMTP id 6A6E24Zs018748; Fri, 6 Nov 2026 17:02:05 +0300 DKIM-Filter: OpenDKIM Filter v2.11.0 mail.openvz.org 6A6E24Zs018748 Authentication-Results: mail.openvz.org; dkim=fail reason="signature verification failed" (2048-bit key) header.d=virtuozzo.com header.i=@virtuozzo.com header.b="xbnHNqFp" Received: from mail-wr1-f72.google.com (mail-wr1-f72.google.com [209.85.221.72]) by mail.openvz.org (8.14.4/8.14.4) with ESMTP id 6A6E1iaq018709 (version=TLSv1/SSLv3 cipher=AES128-GCM-SHA256 bits=128 verify=FAIL) for ; Fri, 6 Nov 2026 17:01:44 +0300 DKIM-Filter: OpenDKIM Filter v2.11.0 mail.openvz.org 6A6E1iaq018709 Received: by mail-wr1-f72.google.com with SMTP id ffacd0b85a97d-490c69dc02bso626466f8f.1 for ; Fri, 06 Nov 2026 06:01:44 -0800 (PST) X-Forwarded-Encrypted: i=2; AL+hErGi7vCFyfpfIXl9w6WVFLWyOLgdU/ZfuOMPn6fxcbN+gNyEDEMwmabqlbjJ30zvi5PRomv0Cg==@openvz.org X-Gm-Message-State: APuU4Z+LipKo9h2FrwH9v4hK23JZ1bl//LCnnJlf6iDovCe7IdcxCrNU S9DMPVVWD1j/lufha27SUueZvpoE7E3S2MirMQqR0uz/06zqxuyBhuthvwISX/SZ6C8mQiYnCAS xtPB/VmvZPqO7Eitor2XlWrzDBhmZNx/P8gQtCfQe/bC4A9rJ40Wkfw== X-Gm-Gg: AYBFou1Lth7xKDGDcbbGLkCFjGzWfk0Ng+wYzTUK9spLhoCYFyHloQVGSz3zXHARPHe /uUY/MEAhXjV6R47mou/t+en/N4WfXCwFKNNXqM7gFqkEWSTqK4kOvFPw1pVOpdNJe2NLcV/tjY EeuQYcTZb/ZJEEsz2D5NTxX6Ft2GbzNHB3mxGBg7kX9qVfYik32Blk5Mnl7fC1FMWZdVsTGlcDJ HA+8C+no+AMsKjTgSzLw8MsRxkiwwJsbI0oV2fTLrrKGm9wMvvsRkFQCWjGCy10/IZknb3jjFJ/ UohcGGCFirEQZLncci9eU66c07560yVhqfFRZRXPQbxzBIyiMcFiEUdbsS8kApvMiKfhsX+9WJL teN17D49QOXudcKVs0Q== X-Received: by 2002:a05:6000:5c9:b0:48e:75f:477d with SMTP id ffacd0b85a97d-49273e5b2eemr5394631f8f.7.1793973704278; Fri, 06 Nov 2026 06:01:44 -0800 (PST) X-Received: by 2002:a05:6000:5c9:b0:48e:75f:477d with SMTP id ffacd0b85a97d-49273e5b2eemr5394584f8f.7.1793973703661; Fri, 06 Nov 2026 06:01:43 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1793973703; cv=none; d=google.com; s=arc-20260327; b=rjB1l8dFjhrFM1p18YOAFNH9e6jNNw1C3KvgVROfrjuwiYp0tzzoK9NZMTnZQ83TLs J7vSkS+sq2GfQbZsJkrTZucWP8hP4ZeKRzAmcgrkU67cb32/MGAT2BnGBSS/hwCVDmK0 iXcvde33FqFXXivv8B1mCQcxFfMvuffYZVqiUD5Jqg2jgv6maBTBdMhoId6LYiyHo98Q 50SqcoebfyhmlIKxwzaxutWEN7JqRcNAwkW4r8Lz2vpws0j0Tuj4yHRrgjSiZybVCKI8 tSgLNZuTDS1u0Oq82wfB2Tg9GHUgQXAFg+me509P5UH7tRqrUImjIRlijfA2qAiVglbV PnFA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20260327; h=cc:to:in-reply-to:references:message-id:content-transfer-encoding :mime-version:subject:date:from:dkim-signature; bh=hriiyGEG0wXhybR4jMZHPMMRJ2/kZPl6VsyOUEQrqH4=; fh=bRkZfFa6377EgOVW8zBDri2gGIQqe/ZeiH+ijEM/ROI=; b=rfRBo57UkC7y5svswCsYLDx+6rCTc6pO1NAlzp2r0pJUde7sQqNT/rsM9Aj8pw3ySB mnfO7McGC4j3A9MRbWzV9vcdXS3E2BT0ZuJha07Tdx/N32hs27hLy3VcuQbTr1LhG1Gs gXxxbmtnSSbOiVd8R9yVfyKV+JGco+UVl/zgnetvFEahiM4QFlqQxW0/ngQcPfOMQu3U ikCKmWhxh7aja8zPQ9BI6dhZfwhz2prkDPO5o3IV+Z+c2HTbt1p1Svt6mSdV8ySiAzgB NuHFww4g4ygvfgBzM9SNCPGK26abj2tWpQMKC/1eKadgCuAy0R4/LI4MrjHMtzAcwQ42 74+A==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@virtuozzo.com header.s=relay header.b=xbnHNqFp; spf=pass (google.com: domain of khorenko@virtuozzo.com designates 130.117.225.111 as permitted sender) smtp.mailfrom=khorenko@virtuozzo.com; dmarc=pass (p=QUARANTINE sp=QUARANTINE dis=NONE) header.from=virtuozzo.com Received: from relay.virtuozzo.com (relay.virtuozzo.com. [130.117.225.111]) by mx.google.com with ESMTPS id ffacd0b85a97d-492d741e389si3519449f8f.253.2026.11.06.06.01.43 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 06 Nov 2026 06:01:43 -0800 (PST) Received-SPF: pass (google.com: domain of khorenko@virtuozzo.com designates 130.117.225.111 as permitted sender) client-ip=130.117.225.111; Authentication-Results: mx.google.com; dkim=pass header.i=@virtuozzo.com header.s=relay header.b=xbnHNqFp; spf=pass (google.com: domain of khorenko@virtuozzo.com designates 130.117.225.111 as permitted sender) smtp.mailfrom=khorenko@virtuozzo.com; dmarc=pass (p=QUARANTINE sp=QUARANTINE dis=NONE) header.from=virtuozzo.com DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=virtuozzo.com; s=relay; h=Message-Id:Content-Type:MIME-Version:Subject:Date :From; bh=hriiyGEG0wXhybR4jMZHPMMRJ2/kZPl6VsyOUEQrqH4=; b=xbnHNqFprWWTPZzwj3d DnYLzTOBu76cXBLfRsLz/Rd+wArcKgotHAgv3F5Y00h+lv+k6neNxJTLBRkW0XkBosUWW8Whh5RRP BtfCtOrIzmxqmrvinyeTE85WKB/thW1J/2h1wd484hWAN1CZ3cILiwQRROko8+XhrltDxPPVrfEPm ZQwXvzMLxNr8/6lTAx0fEICmrlPo/PwEktJrlfRErf0ozAXgePuwPz8ARrpDNaT9MEOueb/J/OoYO 1P3yXQ2ZxpBvifHywwKJnOQk8VCbcMKUaMTTrpwei7Zb45IsAmq7qo5DS3W5zLaxo4qIm3r+wcPpb U7x11UDjWMKEmSg==; Received: from ch-demo-asa.virtuozzo.com ([130.117.225.8] helo=f0.sw.ru) by relay.virtuozzo.com with esmtp (Exim 4.96) (envelope-from ) id 1xPKRj-00BceL-0r; Fri, 06 Nov 2026 15:01:39 +0100 From: Konstantin Khorenko Date: Fri, 06 Nov 2026 15:01:33 +0100 MIME-Version: 1.0 Message-Id: <20261106-b4-prep-khorenko-vstor-153679-mbind-ve-v2-2-6327b23a2d93@virtuozzo.com> References: <20261106-b4-prep-khorenko-vstor-153679-mbind-ve-v2-0-6327b23a2d93@virtuozzo.com> In-Reply-To: <20261106-b4-prep-khorenko-vstor-153679-mbind-ve-v2-0-6327b23a2d93@virtuozzo.com> To: Pavel Tikhomirov , Vasileios Almpanis X-Mailer: b4 0.16.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=6955; i=khorenko@virtuozzo.com; h=from:subject:message-id; bh=RFI644ihQwrTiMXA64VHGDScyYDpE6nIIxKsQH1jjSI=; b=owEBbAKT/ZANAwAKAVGWCkf5YVwqAcsmYgBq7d3F8E8XOYk4TbZ0XGiQnXia2Y3CSLB/t6/SX mwvDyl7mZqJAjIEAAEKAB0WIQRWD23IPcXT0GO9CCxRlgpH+WFcKgUCau3dxQAKCRBRlgpH+WFc KvouD/dnWQf740ORHkFm9m9UbJStWA6DHf61qoocJlf8C4odlWIWUeFeaFm2T0w9HIHhkIPWLU4 7wm+p+OhDYAxMgXLM30+V45GUzuD9uNOotRBKX8DtxPB62A5NiYE6XERBFEYLx/t97UKzIGHLbA eQz4TVwTgsjshGBbyjBDYnXkQKizCzl2vNR5Co0lbT5jF56y/29shf7AXX1FmlMuWTEkA0SP6DU kT5s9iRWXFlkGKO/byA+QRp7sCJOrAVOCuddyuYejYdaYDjcWTiNh2o6GA52j/tvw9OI8JbkU1p ZgMVpX0yfAZvaZjeMaJL3byKZKxBVWmOhxcNwGYsboaJkMINA6DL9HdP++xPR8XHxcnPeHSw82f K+fsUvBPy+OqA56H8OEEKLXxOkw6ttGXHLr/D1WNhnzyuDmF+ZTlOG5uIrGWFXIGKxoE9PiN2Gq pL4Ki+k/jezb+aqoE9qK9ObpoP6vG2DSXBiYp65BnzVLIjvO8FGgqlMGqr1Jz6mI7uKny1JFtn+ wrmvw5eL1F3fNOxNrScsj5CGd+2p5ZE6uw9TeQkEXdvnA1neZ23cDiAf8OFGAY6eySaervVJTT6 UeupkBp71sabcQEx0Nj1ny3vaQatYi3D13LuOdFKoUlrKNPz75q9HpnGLn89bIwJDyoAbcC6cAx dR27xtjpb/Ube X-Developer-Key: i=khorenko@virtuozzo.com; a=openpgp; fpr=560F6DC83DC5D3D063BD082C51960A47F9615C2A X-OZ-Fwd: true Cc: devel@openvz.org Subject: [Devel] [PATCH hci-8.1 v2 2/4] selftests/ve: check that the NUMA API syscalls return ENOSYS in a VE X-BeenThere: devel@openvz.org X-Mailman-Version: 2.1.12 Precedence: list List-Id: OpenVZ development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Sender: devel-bounces@openvz.org Errors-To: devel-bounces@openvz.org A CT must see a kernel without NUMA, so all six NUMA API syscalls return -ENOSYS in a non-super VE. The test makes each call with arguments that succeed on the host and checks that the host gets 0, while a task in a VE gets -ENOSYS. The host result shows that the ENOSYS can only come from the VE check, not from a bad argument. https://virtuozzo.atlassian.net/browse/VSTOR-153679 Feature: mm: prohibit NUMA API inside CT Signed-off-by: Konstantin Khorenko --- tools/testing/selftests/ve/.gitignore | 1 + tools/testing/selftests/ve/Makefile | 1 + .../ve/ve_numa_syscalls_prohibited_test.c | 196 +++++++++++++++++++++ 3 files changed, 198 insertions(+) diff --git a/tools/testing/selftests/ve/.gitignore b/tools/testing/selftests/ve/.gitignore index 3d1179bd2c5f4..5e07985c8fed3 100644 --- a/tools/testing/selftests/ve/.gitignore +++ b/tools/testing/selftests/ve/.gitignore @@ -4,3 +4,4 @@ ve_mount_accounting_test ve_cpuid_override_test ve_vtty_stress ve_numa_migrate_test +ve_numa_syscalls_prohibited_test diff --git a/tools/testing/selftests/ve/Makefile b/tools/testing/selftests/ve/Makefile index e96320a183844..451a7e1cc17d1 100644 --- a/tools/testing/selftests/ve/Makefile +++ b/tools/testing/selftests/ve/Makefile @@ -7,6 +7,7 @@ TEST_GEN_PROGS += ve_perms_test TEST_GEN_PROGS += ve_mount_accounting_test TEST_GEN_PROGS += ve_vtty_stress TEST_GEN_PROGS += ve_numa_migrate_test +TEST_GEN_PROGS += ve_numa_syscalls_prohibited_test # CPUID faulting is x86-64 only. ARCH says "x86" for 32-bit too and lib.mk # picks the clang target by its emptiness, so decide by the compiler. diff --git a/tools/testing/selftests/ve/ve_numa_syscalls_prohibited_test.c b/tools/testing/selftests/ve/ve_numa_syscalls_prohibited_test.c new file mode 100644 index 0000000000000..c76fcb1c79ff7 --- /dev/null +++ b/tools/testing/selftests/ve/ve_numa_syscalls_prohibited_test.c @@ -0,0 +1,196 @@ +// SPDX-License-Identifier: GPL-2.0 +/* Every NUMA API syscall works on the host and returns ENOSYS in a VE. */ +#define _GNU_SOURCE +#include +#include +#include +#include +#include +#include +#include +#include + +#include "../kselftest_harness.h" +#include "ve_selftest.h" + +#define NODE_BITS 1024 +#define LONG_BITS (8 * sizeof(unsigned long)) + +static unsigned long node_mask[NODE_BITS / LONG_BITS]; +static void *page; +static size_t page_size; + +static long call_get_mempolicy(void) +{ + int mode; + + return syscall(__NR_get_mempolicy, &mode, NULL, 0UL, 0UL, 0UL); +} + +static long call_set_mempolicy(void) +{ + return syscall(__NR_set_mempolicy, MPOL_DEFAULT, NULL, 0UL); +} + +static long call_mbind(void) +{ + return syscall(__NR_mbind, page, page_size, MPOL_BIND, node_mask, + NODE_BITS + 1UL, 0U); +} + +static long call_set_mempolicy_home_node(void) +{ + unsigned long node; + + for (node = 0; node < NODE_BITS; node++) + if (node_mask[node / LONG_BITS] & (1UL << (node % LONG_BITS))) + break; + return syscall(__NR_set_mempolicy_home_node, page, page_size, node, 0UL); +} + +static long call_migrate_pages(void) +{ + unsigned long none[NODE_BITS / LONG_BITS] = { 0 }; + + return syscall(__NR_migrate_pages, 0, NODE_BITS + 1UL, none, node_mask); +} + +static long call_move_pages(void) +{ + return syscall(__NR_move_pages, 0, 0UL, NULL, NULL, NULL, 0); +} + +/* set_mempolicy_home_node() needs the MPOL_BIND policy mbind() installs. */ +static const struct numa_call { + const char *name; + long (*call)(void); +} numa_calls[] = { + { "get_mempolicy", call_get_mempolicy }, + { "set_mempolicy", call_set_mempolicy }, + { "mbind", call_mbind }, + { "set_mempolicy_home_node", call_set_mempolicy_home_node }, + { "migrate_pages", call_migrate_pages }, + { "move_pages", call_move_pages }, +}; + +#define NR_CALLS ARRAY_SIZE(numa_calls) + +struct call_result { + long ret; + int err; +}; + +static void run_calls(struct call_result *res) +{ + unsigned int i; + + for (i = 0; i < NR_CALLS; i++) { + errno = 0; + res[i].ret = numa_calls[i].call(); + res[i].err = errno; + } +} + +FIXTURE(numa_syscalls) +{ + int cgv2_fd; + int ctid; +}; + +FIXTURE_SETUP(numa_syscalls) +{ + unsigned long allowed[NODE_BITS / LONG_BITS] = { 0 }; + unsigned int i; + long ret; + + self->cgv2_fd = -1; + + if (geteuid() != 0) + SKIP(return, "creating a ve cgroup needs root"); + + page_size = getpagesize(); + page = mmap(NULL, page_size, PROT_READ | PROT_WRITE, + MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); + ASSERT_NE(page, MAP_FAILED); + + ret = syscall(__NR_get_mempolicy, NULL, allowed, NODE_BITS + 1UL, 0UL, + MPOL_F_MEMS_ALLOWED); + if (ret == -1 && errno == ENOSYS) + SKIP(return, "no NUMA API on the host"); + ASSERT_EQ(ret, 0); + for (i = 0; i < NODE_BITS; i++) { + if (allowed[i / LONG_BITS] & (1UL << (i % LONG_BITS))) { + node_mask[i / LONG_BITS] = 1UL << (i % LONG_BITS); + break; + } + } + ASSERT_LT(i, NODE_BITS); + + self->cgv2_fd = mount_cg2_fd(); + ASSERT_GE(self->cgv2_fd, 0); + ASSERT_EQ(write_file_at(self->cgv2_fd, "cgroup.subtree_control", + VE_CONTROLLERS), 0); + + self->ctid = make_ve(self->cgv2_fd, CTID_MIN); + ASSERT_GE(self->ctid, 0); +} + +FIXTURE_TEARDOWN(numa_syscalls) +{ + if (self->cgv2_fd >= 0) { + destroy_ve(self->cgv2_fd, self->ctid); + close(self->cgv2_fd); + } +} + +TEST_F(numa_syscalls, host_calls_succeed) +{ + struct call_result res[NR_CALLS]; + unsigned int i; + + run_calls(res); + for (i = 0; i < NR_CALLS; i++) { + EXPECT_EQ(res[i].ret, 0) + TH_LOG("%s on the host: %s", numa_calls[i].name, + strerror(res[i].err)); + } +} + +TEST_F(numa_syscalls, ve_calls_return_enosys) +{ + struct call_result res[NR_CALLS]; + int pipefd[2], status; + unsigned int i; + pid_t pid; + + ASSERT_EQ(pipe(pipefd), 0); + pid = fork(); + ASSERT_GE(pid, 0); + if (pid == 0) { + close(pipefd[0]); + if (enter_cgroup(self->cgv2_fd, self->ctid) < 0) + _exit(1); + if (unshare(CLONE_NEWVE) < 0) + _exit(2); + run_calls(res); + if (write(pipefd[1], res, sizeof(res)) != sizeof(res)) + _exit(3); + _exit(0); + } + close(pipefd[1]); + ASSERT_EQ(waitpid(pid, &status, 0), pid); + ASSERT_TRUE(WIFEXITED(status)); + ASSERT_EQ(WEXITSTATUS(status), 0) + TH_LOG("VE child setup failed at step %d", WEXITSTATUS(status)); + ASSERT_EQ(read(pipefd[0], res, sizeof(res)), sizeof(res)); + close(pipefd[0]); + + for (i = 0; i < NR_CALLS; i++) { + EXPECT_TRUE(res[i].ret == -1 && res[i].err == ENOSYS) + TH_LOG("%s in a VE: returned %ld (%s), expected ENOSYS", + numa_calls[i].name, res[i].ret, + strerror(res[i].err)); + } +} + +TEST_HARNESS_MAIN -- 2.43.0 _______________________________________________ Devel mailing list Devel@openvz.org https://lists.openvz.org/mailman/listinfo/devel