Patch Detail
get:
Show a patch.
patch:
Update a patch.
put:
Update a patch.
GET /api/patches/2196326/?format=api
{ "id": 2196326, "url": "http://patchwork.ozlabs.org/api/patches/2196326/?format=api", "web_url": "http://patchwork.ozlabs.org/project/ltp/patch/20260213131328.122625-2-piotr.kubaj@intel.com/", "project": { "id": 59, "url": "http://patchwork.ozlabs.org/api/projects/59/?format=api", "name": "Linux Test Project development", "link_name": "ltp", "list_id": "ltp.lists.linux.it", "list_email": "ltp@lists.linux.it", "web_url": "", "scm_url": "", "webscm_url": "", "list_archive_url": "", "list_archive_url_format": "", "commit_url_format": "" }, "msgid": "<20260213131328.122625-2-piotr.kubaj@intel.com>", "list_archive_url": null, "date": "2026-02-13T13:13:29", "name": "[v6] thermal: add new test group", "commit_ref": null, "pull_url": null, "state": "needs-review-ack", "archived": false, "hash": "11bd3754b9c869d150d713c61b42e795001e4de4", "submitter": { "id": 92049, "url": "http://patchwork.ozlabs.org/api/people/92049/?format=api", "name": "Piotr Kubaj", "email": "piotr.kubaj@intel.com" }, "delegate": null, "mbox": "http://patchwork.ozlabs.org/project/ltp/patch/20260213131328.122625-2-piotr.kubaj@intel.com/mbox/", "series": [ { "id": 492093, "url": "http://patchwork.ozlabs.org/api/series/492093/?format=api", "web_url": "http://patchwork.ozlabs.org/project/ltp/list/?series=492093", "date": "2026-02-13T13:13:29", "name": "[v6] thermal: add new test group", "version": 6, "mbox": "http://patchwork.ozlabs.org/series/492093/mbox/" } ], "comments": "http://patchwork.ozlabs.org/api/patches/2196326/comments/", "check": "success", "checks": "http://patchwork.ozlabs.org/api/patches/2196326/checks/", "tags": {}, "related": [], "headers": { "Return-Path": "<ltp-bounces+incoming=patchwork.ozlabs.org@lists.linux.it>", "X-Original-To": [ "incoming@patchwork.ozlabs.org", "ltp@lists.linux.it" ], "Delivered-To": [ "patchwork-incoming@legolas.ozlabs.org", "ltp@picard.linux.it" ], "Authentication-Results": [ "legolas.ozlabs.org;\n\tdkim=fail reason=\"signature verification failed\" (2048-bit key;\n unprotected) header.d=intel.com header.i=@intel.com header.a=rsa-sha256\n header.s=Intel header.b=R3A6j7ov;\n\tdkim-atps=neutral", "legolas.ozlabs.org;\n spf=pass (sender SPF authorized) smtp.mailfrom=lists.linux.it\n (client-ip=213.254.12.146; helo=picard.linux.it;\n envelope-from=ltp-bounces+incoming=patchwork.ozlabs.org@lists.linux.it;\n receiver=patchwork.ozlabs.org)" ], "Received": [ "from picard.linux.it (picard.linux.it [213.254.12.146])\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 4fCCLx1xK4z1xr1\n\tfor <incoming@patchwork.ozlabs.org>; Sat, 14 Feb 2026 00:14:48 +1100 (AEDT)", "from picard.linux.it (localhost [IPv6:::1])\n\tby picard.linux.it (Postfix) with ESMTP id 4D7183CF83B\n\tfor <incoming@patchwork.ozlabs.org>; Fri, 13 Feb 2026 14:14:45 +0100 (CET)", "from in-2.smtp.seeweb.it (in-2.smtp.seeweb.it\n [IPv6:2001:4b78:1:20::2])\n (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)\n key-exchange X25519 server-signature ECDSA (secp384r1) server-digest SHA384)\n (No client certificate requested)\n by picard.linux.it (Postfix) with ESMTPS id E51823CF7C0\n for <ltp@lists.linux.it>; Fri, 13 Feb 2026 14:14:40 +0100 (CET)", "from mgamail.intel.com (mgamail.intel.com [192.198.163.7])\n (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits))\n (No client certificate requested)\n by in-2.smtp.seeweb.it (Postfix) with ESMTPS id 8E203600FFB\n for <ltp@lists.linux.it>; Fri, 13 Feb 2026 14:14:38 +0100 (CET)", "from orviesa008.jf.intel.com ([10.64.159.148])\n by fmvoesa101.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384;\n 13 Feb 2026 05:14:36 -0800", "from pkubaj-desk.igk.intel.com (HELO intel.com) ([10.217.160.221])\n by orviesa008-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384;\n 13 Feb 2026 05:14:35 -0800" ], "DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/simple;\n d=intel.com; i=@intel.com; q=dns/txt; s=Intel;\n t=1770988480; x=1802524480;\n h=from:to:cc:subject:date:message-id:mime-version:\n content-transfer-encoding;\n bh=seFNhnjCr/1tB6Dw5nIG5/LIOD5VmFc2gCh3Sv4n8o4=;\n b=R3A6j7oviCRpkDNqpB9OV1VBEGhmOX52lbbqM02W0O+Az+lzPwcGYn9Z\n hksxbJjnGnSGlXLnGYg1QnyAMQpQAieK4AuR+Z8377139oA8CgRxTHqob\n 6iULpKuRWbw72s4Xr0Se+x0dQU6JdTah1MVi1wTfETmIsijxZTUZFaTfL\n RP1H9dzdxGis7eNauj3EZhbwy6Rn12sgUKCNUlXd84iTD6WUUmMOt7mGd\n 2KjxZz/V286mEDoWsIwLqFeyPnxxIqND2Lq2c1qQO6iw/CXMYztgW7g9T\n JLpPq9P0gzevtfATeTcw6ROCH2zX6GgaMxj4kGNk8FI6bWzFJt1EjkfQS w==;", "X-CSE-ConnectionGUID": [ "TgBG0eZbRE2sSoyJ46KweA==", "dxxYIQh1QAShWUWhPitJOQ==" ], "X-CSE-MsgGUID": [ "r+YhEzS3RaKq+YKKoXqFzA==", "UXu857M2Q2ymsAbBi3ioiA==" ], "X-IronPort-AV": [ "E=McAfee;i=\"6800,10657,11700\"; a=\"97630152\"", "E=Sophos;i=\"6.21,288,1763452800\"; d=\"scan'208\";a=\"97630152\"", "E=Sophos;i=\"6.21,288,1763452800\"; d=\"scan'208\";a=\"212946925\"" ], "X-ExtLoop1": "1", "From": "Piotr Kubaj <piotr.kubaj@intel.com>", "To": "ltp@lists.linux.it", "Date": "Fri, 13 Feb 2026 14:13:29 +0100", "Message-ID": "<20260213131328.122625-2-piotr.kubaj@intel.com>", "X-Mailer": "git-send-email 2.47.3", "MIME-Version": "1.0", "X-Spam-Status": "No, score=0.1 required=7.0 tests=DKIM_SIGNED,DKIM_VALID,\n DKIM_VALID_AU,DKIM_VALID_EF,DMARC_PASS,SPF_HELO_NONE,SPF_PASS\n shortcircuit=no autolearn=disabled version=4.0.1", "X-Spam-Checker-Version": "SpamAssassin 4.0.1 (2024-03-25) on in-2.smtp.seeweb.it", "X-Virus-Scanned": "clamav-milter 1.0.9 at in-2.smtp.seeweb.it", "X-Virus-Status": "Clean", "Subject": "[LTP] [PATCH v6] thermal: add new test group", "X-BeenThere": "ltp@lists.linux.it", "X-Mailman-Version": "2.1.29", "Precedence": "list", "List-Id": "Linux Test Project <ltp.lists.linux.it>", "List-Unsubscribe": "<https://lists.linux.it/options/ltp>,\n <mailto:ltp-request@lists.linux.it?subject=unsubscribe>", "List-Archive": "<http://lists.linux.it/pipermail/ltp/>", "List-Post": "<mailto:ltp@lists.linux.it>", "List-Help": "<mailto:ltp-request@lists.linux.it?subject=help>", "List-Subscribe": "<https://lists.linux.it/listinfo/ltp>,\n <mailto:ltp-request@lists.linux.it?subject=subscribe>", "Cc": "helena.anna.dubel@intel.com, tomasz.ossowski@intel.com,\n rafael.j.wysocki@intel.com, daniel.niestepski@intel.com", "Content-Type": "text/plain; charset=\"us-ascii\"", "Content-Transfer-Encoding": "7bit", "Errors-To": "ltp-bounces+incoming=patchwork.ozlabs.org@lists.linux.it", "Sender": "\"ltp\" <ltp-bounces+incoming=patchwork.ozlabs.org@lists.linux.it>" }, "content": "This is a new test for checking thermal interrupt events.\nI added some fixes suggested by Petr Vorel. Since no one else\nreviewed this code and two weeks have passed, I'm sending the\ncorrected version.\n\nSigned-off-by: Piotr Kubaj <piotr.kubaj@intel.com>\n---\n runtest/thermal | 3 +\n scenario_groups/default | 1 +\n testcases/kernel/Makefile | 1 +\n testcases/kernel/thermal/Makefile | 9 +\n .../kernel/thermal/thermal_interrupt_events.c | 209 ++++++++++++++++++\n 5 files changed, 223 insertions(+)\n create mode 100644 runtest/thermal\n create mode 100644 testcases/kernel/thermal/Makefile\n create mode 100644 testcases/kernel/thermal/thermal_interrupt_events.c", "diff": "diff --git a/runtest/thermal b/runtest/thermal\nnew file mode 100644\nindex 000000000..57e3d29f8\n--- /dev/null\n+++ b/runtest/thermal\n@@ -0,0 +1,3 @@\n+# Thermal driver API\n+# https://docs.kernel.org/driver-api/thermal/\n+thermal_interrupt_events thermal_interrupt_events\ndiff --git a/scenario_groups/default b/scenario_groups/default\nindex 0e76b2bee..ffdd7ff25 100644\n--- a/scenario_groups/default\n+++ b/scenario_groups/default\n@@ -26,3 +26,4 @@ crypto\n kernel_misc\n uevent\n watchqueue\n+thermal\ndiff --git a/testcases/kernel/Makefile b/testcases/kernel/Makefile\nindex 98fd45a9d..ac816e4e8 100644\n--- a/testcases/kernel/Makefile\n+++ b/testcases/kernel/Makefile\n@@ -36,6 +36,7 @@ SUBDIRS\t\t\t+= connectors \\\n \t\t\t sched \\\n \t\t\t security \\\n \t\t\t sound \\\n+\t\t\t thermal \\\n \t\t\t tracing \\\n \t\t\t uevents \\\n \t\t\t watchqueue \\\ndiff --git a/testcases/kernel/thermal/Makefile b/testcases/kernel/thermal/Makefile\nnew file mode 100644\nindex 000000000..4657c3fb3\n--- /dev/null\n+++ b/testcases/kernel/thermal/Makefile\n@@ -0,0 +1,9 @@\n+# SPDX-License-Identifier: GPL-2.0-or-later\n+# Copyright (c) 2025, Intel Corporation. All rights reserved.\n+# Author:Piotr Kubaj <piotr.kubaj@intel.com>\n+\n+top_srcdir ?= ../../..\n+\n+include $(top_srcdir)/include/mk/testcases.mk\n+\n+include $(top_srcdir)/include/mk/generic_leaf_target.mk\ndiff --git a/testcases/kernel/thermal/thermal_interrupt_events.c b/testcases/kernel/thermal/thermal_interrupt_events.c\nnew file mode 100644\nindex 000000000..d9105ff63\n--- /dev/null\n+++ b/testcases/kernel/thermal/thermal_interrupt_events.c\n@@ -0,0 +1,209 @@\n+// SPDX-License-Identifier: GPL-2.0-or-later\n+\n+/*\n+ * Copyright (C) 2025-2026 Intel - http://www.intel.com/\n+ */\n+\n+/*\\\n+ * Tests the CPU package thermal sensor interface for Intel platforms.\n+\n+ * Works by checking the initial count of thermal interrupts. Then it\n+ * decreases the threshold for sending a thermal interrupt to just above\n+ * the current temperature and runs a workload on the CPU. Finally, it restores\n+ * the original thermal threshold and checks whether the number of thermal\n+ * interrupts increased.\n+ */\n+\n+#include \"tst_safe_stdio.h\"\n+#include \"tst_test.h\"\n+\n+#define\tRUNTIME\t\t30\n+#define\tSLEEP\t\t10\n+#define\tTEMP_INCREMENT\t10\n+\n+static bool x86_pkg_temp_tz_found, *x86_pkg_temp_tz, status = 1;\n+static char temp_path[NAME_MAX], trip_path[NAME_MAX];\n+static int nproc, temp_high, temp, trip, tz_counter;\n+static uint64_t *interrupt_init, *interrupt_later;\n+\n+static void read_interrupts(uint64_t *interrupts, const int nproc)\n+{\n+\tbool interrupts_found = false;\n+\tchar line[8192];\n+\n+\tmemset(interrupts, 0, nproc * sizeof(*interrupts));\n+\tFILE *fp = SAFE_FOPEN(\"/proc/interrupts\", \"r\");\n+\n+\twhile (fgets(line, sizeof(line), fp)) {\n+\t\tif (strstr(line, \"Thermal event interrupts\")) {\n+\t\t\tinterrupts_found = true;\n+\t\t\tchar *token = strtok(line, \" \");\n+\n+\t\t\ttoken = strtok(NULL, \" \");\n+\t\t\tint i = 0;\n+\n+\t\t\twhile (!!strncmp(token, \"Thermal\", 7)) {\n+\t\t\t\tinterrupts[i++] = atoll(token);\n+\t\t\t\ttoken = strtok(NULL, \" \");\n+\t\t\t\ttst_res(TDEBUG, \"interrupts[%d]: %ld\", i - 1, interrupts[i - 1]);\n+\t\t\t}\n+\t\t\tbreak;\n+\t\t}\n+\t}\n+\tSAFE_FCLOSE(fp);\n+\tif (!interrupts_found)\n+\t\ttst_brk(TCONF, \"No Thermal event interrupts line in /proc/interrupts\");\n+}\n+\n+static void setup(void)\n+{\n+\tchar line[8192];\n+\n+\tnproc = tst_ncpus();\n+\ttst_res(TDEBUG, \"Number of logical cores: %d\", nproc);\n+\tinterrupt_init = calloc(nproc, sizeof(uint64_t));\n+\tinterrupt_later = calloc(nproc, sizeof(uint64_t));\n+\n+\tDIR *dir = SAFE_OPENDIR(\"/sys/class/thermal/\");\n+\tstruct dirent *entry;\n+\n+\twhile ((entry = SAFE_READDIR(dir))) {\n+\t\tif ((strncmp(entry->d_name, \"thermal_zone\", sizeof(\"thermal_zone\"))) > 0)\n+\t\t\ttz_counter++;\n+\t}\n+\tSAFE_CLOSEDIR(dir);\n+\ttst_res(TDEBUG, \"Found %d thermal zone(s)\", tz_counter);\n+\n+\tread_interrupts(interrupt_init, nproc);\n+\n+\tx86_pkg_temp_tz = calloc(tz_counter, sizeof(bool));\n+\n+\tfor (int i = 0; i < tz_counter; i++) {\n+\t\tchar path[NAME_MAX];\n+\n+\t\tsnprintf(path, NAME_MAX, \"/sys/class/thermal/thermal_zone%d/type\", i);\n+\t\ttst_res(TDEBUG, \"Checking whether %s is x86_pkg_temp\", path);\n+\n+\t\tSAFE_FILE_SCANF(path, \"%s\", line);\n+\t\tif (strstr(line, \"x86_pkg_temp\")) {\n+\t\t\ttst_res(TDEBUG, \"Thermal zone %d uses x86_pkg_temp\", i);\n+\t\t\tx86_pkg_temp_tz[i] = 1;\n+\t\t\tx86_pkg_temp_tz_found = 1;\n+\t\t}\n+\t}\n+\n+\tif (!x86_pkg_temp_tz_found)\n+\t\ttst_brk(TCONF, \"No thermal zone uses x86_pkg_temp\");\n+}\n+\n+static void *cpu_workload(double run_time)\n+{\n+\ttime_t start_time = time(NULL);\n+\tint num = 2;\n+\n+\twhile (difftime(time(NULL), start_time) < run_time) {\n+\t\tfor (int i = 2; i * i <= num; i++) {\n+\t\t\tif (num % i == 0)\n+\t\t\t\tbreak;\n+\t\t}\n+\t\tnum++;\n+\t\tSAFE_FILE_SCANF(temp_path, \"%d\", &temp);\n+\n+\t\tif (temp > temp_high)\n+\t\t\tbreak;\n+\t}\n+\treturn NULL;\n+}\n+\n+static void test_zone(int i)\n+{\n+\t\t\tchar path[NAME_MAX];\n+\t\t\tint sleep_time = SLEEP;\n+\t\t\tdouble run_time = RUNTIME;\n+\n+\t\t\tsnprintf(path, NAME_MAX, \"/sys/class/thermal/thermal_zone%d/\", i);\n+\t\t\tstrncpy(temp_path, path, NAME_MAX);\n+\t\t\tstrncat(temp_path, \"temp\", 4);\n+\t\t\ttst_res(TINFO, \"Testing %s\", temp_path);\n+\t\t\tSAFE_FILE_SCANF(temp_path, \"%d\", &temp);\n+\t\t\tif (temp < 0) {\n+\t\t\t\ttst_brk(TBROK, \"Unexpected zone temperature value %d\", temp);\n+\t\t\t\tstatus = 0;\n+\t\t\t}\n+\t\t\ttst_res(TDEBUG, \"Current temperature for %s: %d\", path, temp);\n+\n+\t\t\ttemp_high = temp + TEMP_INCREMENT;\n+\n+\t\t\tstrncpy(trip_path, path, NAME_MAX);\n+\t\t\tstrncat(trip_path, \"trip_point_1_temp\", 17);\n+\n+\t\t\ttst_res(TDEBUG, \"Setting new trip_point_1_temp value: %d\", temp_high);\n+\t\t\tSAFE_FILE_SCANF(trip_path, \"%d\", &trip);\n+\t\t\tSAFE_FILE_PRINTF(trip_path, \"%d\", temp_high);\n+\n+\t\t\twhile (sleep_time > 0) {\n+\t\t\t\ttst_res(TDEBUG, \"Running for %f seconds, then sleeping for %d seconds\", run_time, sleep_time);\n+\n+\t\t\t\tfor (int j = 0; j < nproc; j++) {\n+\t\t\t\t\tif (!SAFE_FORK()) {\n+\t\t\t\t\t\tcpu_workload(run_time);\n+\t\t\t\t\t\texit(0);\n+\t\t\t\t\t}\n+\t\t\t\t}\n+\n+\t\t\t\ttst_reap_children();\n+\n+\t\t\t\tSAFE_FILE_SCANF(temp_path, \"%d\", &temp);\n+\t\t\t\ttst_res(TDEBUG, \"Temperature for %s after a test: %d\", path, temp);\n+\n+\t\t\t\tif (temp > temp_high)\n+\t\t\t\t\tbreak;\n+\t\t\t\tsleep(sleep_time--);\n+\t\t\t\trun_time -= 3;\n+\t\t\t}\n+\n+\t\t\tif (temp <= temp_high) {\n+\t\t\t\ttst_brk(TFAIL, \"Zone temperature is not rising as expected\");\n+\t\t\t\tstatus = 0;\n+\t\t\t}\n+}\n+\n+static void cleanup(void)\n+{\n+\tif (x86_pkg_temp_tz_found)\n+\t\tSAFE_FILE_PRINTF(trip_path, \"%d\", trip);\n+\tfree(interrupt_init);\n+\tfree(interrupt_later);\n+}\n+\n+static void run(void)\n+{\n+\tfor (int i = 0; i < tz_counter; i++) {\n+\t\tif (x86_pkg_temp_tz[i])\n+\t\t\ttest_zone(i);\n+\t}\n+\tread_interrupts(interrupt_later, nproc);\n+\n+\tfor (int i = 0; i < nproc; i++) {\n+\t\tif (interrupt_later[i] < interrupt_init[i])\n+\t\t\ttst_res(TFAIL, \"CPU %d interrupt counter: %ld (previous: %ld)\",\n+\t\t\t\ti, interrupt_later[i], interrupt_init[i]);\n+\t}\n+\n+\tif (status)\n+\t\ttst_res(TPASS, \"x86 package thermal interrupt triggered\");\n+}\n+\n+static struct tst_test test = {\n+\t.cleanup = cleanup,\n+\t.forks_child = 1,\n+\t.min_runtime = 180,\n+\t.needs_root = 1,\n+\t.setup = setup,\n+\t.supported_archs = (const char *const []) {\n+\t\t\"x86\",\n+\t\t\"x86_64\",\n+\t\tNULL\n+\t},\n+\t.test_all = run\n+};\n", "prefixes": [ "v6" ] }