* [PATCH 1/3] dtc: dt-check-style: Introduce way to disable checks
2026-09-16 20:46 [PATCH 0/3] dtc: dt-check-style: Introduce way to disable checks Krzysztof Kozlowski
@ 2026-09-16 20:46 ` Krzysztof Kozlowski
2026-09-16 20:46 ` [PATCH 2/3] arm64: dts: qcom: Suppress a few intentional redundant whitespaces Krzysztof Kozlowski
2026-09-16 20:46 ` [PATCH 3/3] arm64: dts: exynos5433: " Krzysztof Kozlowski
2 siblings, 0 replies; 5+ messages in thread
From: Krzysztof Kozlowski @ 2026-09-16 20:46 UTC (permalink / raw)
To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Saravana Kannan,
cros-qcom-dts-watchers, Bjorn Andersson, Konrad Dybcio,
Peter Griffin, Alim Akhtar
Cc: linux-kernel, devicetree, linux-arm-msm, linux-arm-kernel,
linux-samsung-soc, Krzysztof Kozlowski
There is a lot of old DTS code, predating stricter DTS Coding Style,
which is not worth fixing, because of impact on backporting changes.
There are also patterns which violate strict rules but make code a bit
more readable.
Introduce shellcheck-style way of disabling specific rules in comments
in DTS:
/* dt-check-style disable=RULE,RULE... */
e.g.
/* dt-check-style disable=redundant-whitespace-strict */
which can be placed in :
1. Top-level comment block of a file: applies to entire DTS file,
2. Before new node: applies to that node only,
3. Before a property: applies to that property only.
Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>
---
scripts/dtc/dt-check-style | 97 +++++++++++++++++++++-
scripts/dtc/dt-style-selftest/bad/dts-suppress.dts | 52 ++++++++++++
.../expected/dts-suppress.dts.txt | 8 ++
.../dt-style-selftest/good/dts-suppress-file.dts | 51 ++++++++++++
.../good/dts-suppress-nodes-properties.dts | 49 +++++++++++
5 files changed, 256 insertions(+), 1 deletion(-)
diff --git a/scripts/dtc/dt-check-style b/scripts/dtc/dt-check-style
index b8c40873905c..96f9c10a70b0 100755
--- a/scripts/dtc/dt-check-style
+++ b/scripts/dtc/dt-check-style
@@ -54,6 +54,8 @@ re_cpp_directive = re.compile(
re_dtc_directive = re.compile(
r'^/(dts-v1|include)/')
+re_check_disable = re.compile(r'\*\s*dt-check-style\s+disable=(\S+)')
+
# label: name@addr { -- label and addr optional; name can be "/"
# Per the DT spec a node name may start with a digit (e.g. 1wire@...).
# The address part is captured loosely (any non-space, non-brace run) so
@@ -342,6 +344,94 @@ class Rule:
self.applies_to = applies_to # input types this rule covers
+class Suppressions:
+ """Parse ``/* dt-check-style disable=RULE,RULE,RULE`` comments.
+
+ Returns a dict mapping line numbers (1-based) to sets of suppressed
+ rule names. Three scopes are recognised:
+
+ - **File-level**: the disable comment appears in the top comments of
+ the block (every line before it is blank or a comment -- no code,
+ no preprocessor directives). The listed rules are suppressed for
+ *every* line in the block.
+
+ - **Node-level**: the disable comment immediately precedes a
+ NODE_OPEN (only blank/comment lines may appear between them). The
+ listed rules are suppressed for all lines from the opening brace to
+ the matching closing brace, inclusive (nested children included).
+
+ - **Property-level**: the disable comment immediately precedes a
+ PROPERTY line. The listed rules are suppressed for that property
+ line and all its continuation lines.
+
+ A disable comment that is not in the top comments and whose next
+ non-comment/non-blank line is neither NODE_OPEN nor PROPERTY is
+ silently ignored.
+ """
+
+ def __init__(self, lines):
+ self.__COMMENT_LIKE = (LineType.BLANK, LineType.COMMENT,
+ LineType.COMMENT_START, LineType.COMMENT_BODY,
+ LineType.COMMENT_END)
+ self.__suppressed = {}
+
+ for i, dl in enumerate(lines):
+ if dl.linetype not in (LineType.COMMENT, LineType.COMMENT_START, LineType.COMMENT_BODY):
+ continue
+ m = re_check_disable.search(dl.stripped)
+ if not m:
+ continue
+ rules = {r for r in m.group(1).split(',') if r}
+ if not rules:
+ continue
+
+ # File-level: every line before this one is blank or a comment.
+ if all(lines[j].linetype in self.__COMMENT_LIKE for j in range(i)):
+ self._suppress_range(lines, 0, len(lines) - 1, rules)
+ continue
+
+ # Find the next non-comment/non-blank line after the disable comment.
+ next_idx = next(
+ (j for j in range(i + 1, len(lines))
+ if lines[j].linetype not in self.__COMMENT_LIKE),
+ None)
+ if next_idx is None:
+ continue
+
+ nxt = lines[next_idx]
+ if nxt.linetype == LineType.NODE_OPEN:
+ # Node-level: suppress from NODE_OPEN to its matching NODE_CLOSE.
+ node_depth = nxt.depth
+ end_idx = len(lines) - 1
+ for j in range(next_idx + 1, len(lines)):
+ if (lines[j].linetype == LineType.NODE_CLOSE and
+ lines[j].depth == node_depth):
+ end_idx = j
+ break
+ self._suppress_range(lines, next_idx, end_idx, rules)
+ elif nxt.linetype == LineType.PROPERTY:
+ # Property-level: suppress the property and its continuations.
+ self._add(nxt.lineno, rules)
+ for cont in nxt.continuations:
+ self._add(cont.lineno, rules)
+
+
+ def _add(self, lineno, rules):
+ self.__suppressed.setdefault(lineno, set()).update(rules)
+
+
+ def _suppress_range(self, lines, start_idx, end_idx, rules):
+ for i in range(start_idx, min(end_idx + 1, len(lines))):
+ dl = lines[i]
+ self._add(dl.lineno, rules)
+ for cont in dl.continuations:
+ self._add(cont.lineno, rules)
+
+
+ def is_suppressed(self, rule_name, lineno):
+ return rule_name in self.__suppressed.get(lineno, set())
+
+
# --- individual rule check functions --------------------------------------
@@ -642,6 +732,9 @@ def check_line_length(ctx):
"""Lines must not exceed 80 columns; tabs count as 8 (see
_display_col)."""
for dl in ctx.lines:
+ # Ignore suppression rules, which can go longer than 80
+ if re_check_disable.search(dl.stripped):
+ continue
yield from _check_line_length(dl)
for cont in dl.continuations:
yield from _check_line_length(cont)
@@ -1180,10 +1273,12 @@ def check_block(text, mode, file_type):
lines = classify_lines(text)
ctx = Ctx(lines, text, mode, file_type)
rules = select_rules(mode, file_type)
+ suppressions = Suppressions(lines)
findings = []
for r in rules:
for lineno, msg in r.check(ctx):
- findings.append((lineno, r.name, msg))
+ if not suppressions.is_suppressed(r.name, lineno):
+ findings.append((lineno, r.name, msg))
findings.sort(key=lambda t: (t[0], t[1]))
return findings
diff --git a/scripts/dtc/dt-style-selftest/bad/dts-suppress.dts b/scripts/dtc/dt-style-selftest/bad/dts-suppress.dts
new file mode 100644
index 000000000000..1602dc74776c
--- /dev/null
+++ b/scripts/dtc/dt-style-selftest/bad/dts-suppress.dts
@@ -0,0 +1,52 @@
+// SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause
+/dts-v1/;
+
+/ {
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ memory@a0000000 {
+ device_type = "memory";
+ reg = <0x0 0xa0000000 0x0 0x0>;
+ };
+
+ /* Wrong rule suppressed */
+ /* dt-check-style disable=child-address-order */
+ a55-pmu {
+ compatible = "example,pmu";
+ };
+
+ soc@0 {
+ compatible = "simple-bus";
+ ranges = <0 0 0 0xc0000000>;
+
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ /* Should not affect the node after this one */
+ /* dt-check-style disable=hex-case */
+ interrupt-controller@10000 {
+ compatible = "example,intc";
+ reg = <0x10000 0x1000>;
+ /* Wrong rule suppressed */
+ /* dt-check-style disable=continuation-alignment */
+ interrupts = <1 2 3>;
+ };
+
+ serial@30000 {
+ compatible = "example,serial";
+ /* dt-check-style disable=continuation-alignment */
+ reg = <0x30000 0xDEAD>,
+ <0x30000 0xDEAD>;
+ /* Ignored suppression not followed by node open or property */
+ /* dt-check-style disable=child-address-order */
+ };
+
+ /* Wrong rule suppressed */
+ /* dt-check-style disable=child-name-order */
+ serial@20000 {
+ compatible = "example,serial";
+ reg = <0x20000 0x1000>;
+ };
+ };
+};
diff --git a/scripts/dtc/dt-style-selftest/expected/dts-suppress.dts.txt b/scripts/dtc/dt-style-selftest/expected/dts-suppress.dts.txt
new file mode 100644
index 000000000000..8d1e7ee4db27
--- /dev/null
+++ b/scripts/dtc/dt-style-selftest/expected/dts-suppress.dts.txt
@@ -0,0 +1,8 @@
+# mode=strict
+bad/dts-suppress.dts:15: [child-name-order] child node 'a55-pmu' out of name order
+bad/dts-suppress.dts:33: [redundant-whitespace-strict] extra whitespace after =
+bad/dts-suppress.dts:39: [hex-case] hex literal '0xDEAD' must be lowercase
+bad/dts-suppress.dts:39: [redundant-whitespace-strict] extra whitespace after =
+bad/dts-suppress.dts:40: [hex-case] hex literal '0xDEAD' must be lowercase
+bad/dts-suppress.dts:47: [child-address-order] child node @20000 out of address order
+bad/dts-suppress.dts:48: [redundant-whitespace-strict] extra whitespace before =
diff --git a/scripts/dtc/dt-style-selftest/good/dts-suppress-file.dts b/scripts/dtc/dt-style-selftest/good/dts-suppress-file.dts
new file mode 100644
index 000000000000..8c3220ed27c7
--- /dev/null
+++ b/scripts/dtc/dt-style-selftest/good/dts-suppress-file.dts
@@ -0,0 +1,51 @@
+// SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause
+/* dt-check-style disable=redundant-whitespace-strict */
+/*
+ * Here goes reason
+ * dt-check-style disable=continuation-alignment
+ */
+/dts-v1/;
+
+/ {
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ memory@a0000000 {
+ device_type = "memory";
+ reg = <0x0 0xa0000000 0x0 0x0>;
+ };
+
+ /* dt-check-style disable=child-name-order */
+ a55-pmu {
+ compatible = "example,pmu";
+ };
+
+ soc@0 {
+ compatible = "simple-bus";
+ ranges = <0 0 0 0xc0000000>;
+
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ interrupt-controller@10000 {
+ compatible = "example,intc";
+ reg = <0x10000 0x1000>;
+ interrupts = <1 2 3>;
+ };
+
+ /* dt-check-style disable=hex-case */
+ serial@30000 {
+ compatible = "example,serial";
+ reg = <0x30000 0xDEAD>,
+ <0x30000 0xDEAD>;
+ };
+
+ /* dt-check-style disable=child-address-order */
+ serial@20000 {
+ compatible = "example,serial";
+ /* Redundant rule disable should be ignored */
+ /* dt-check-style disable=hex-case */
+ reg = <0x20000 0x1000>;
+ };
+ };
+};
diff --git a/scripts/dtc/dt-style-selftest/good/dts-suppress-nodes-properties.dts b/scripts/dtc/dt-style-selftest/good/dts-suppress-nodes-properties.dts
new file mode 100644
index 000000000000..e65b152cfa1e
--- /dev/null
+++ b/scripts/dtc/dt-style-selftest/good/dts-suppress-nodes-properties.dts
@@ -0,0 +1,49 @@
+// SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause
+/dts-v1/;
+
+/ {
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ memory@a0000000 {
+ device_type = "memory";
+ reg = <0x0 0xa0000000 0x0 0x0>;
+ };
+
+ /* dt-check-style disable=child-name-order */
+ a55-pmu {
+ compatible = "example,pmu";
+ };
+
+ soc@0 {
+ compatible = "simple-bus";
+ ranges = <0 0 0 0xc0000000>;
+
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ interrupt-controller@10000 {
+ compatible = "example,intc";
+ reg = <0x10000 0x1000>;
+ /* dt-check-style disable=redundant-whitespace-strict */
+ interrupts = <1 2 3>;
+ };
+
+ /* dt-check-style disable=hex-case */
+ serial@30000 {
+ compatible = "example,serial";
+ /* dt-check-style disable=continuation-alignment,redundant-whitespace-strict */
+ reg = <0x30000 0xDEAD>,
+ <0x30000 0xDEAD>;
+ };
+
+ /* dt-check-style disable=child-address-order */
+ serial@20000 {
+ /* dt-check-style disable=redundant-whitespace-strict */
+ compatible = "example,serial";
+ /* Redundant rule disable should be ignored */
+ /* dt-check-style disable=hex-case */
+ reg = <0x20000 0x1000>;
+ };
+ };
+};
--
2.53.0
^ permalink raw reply [flat|nested] 5+ messages in thread* [PATCH 2/3] arm64: dts: qcom: Suppress a few intentional redundant whitespaces
2026-09-16 20:46 [PATCH 0/3] dtc: dt-check-style: Introduce way to disable checks Krzysztof Kozlowski
2026-09-16 20:46 ` [PATCH 1/3] " Krzysztof Kozlowski
@ 2026-09-16 20:46 ` Krzysztof Kozlowski
2026-09-16 20:52 ` Krzysztof Kozlowski
2026-09-16 20:46 ` [PATCH 3/3] arm64: dts: exynos5433: " Krzysztof Kozlowski
2 siblings, 1 reply; 5+ messages in thread
From: Krzysztof Kozlowski @ 2026-09-16 20:46 UTC (permalink / raw)
To: Rob Herring, Krzysztof Kozlowski, Conor Dooley, Saravana Kannan,
cros-qcom-dts-watchers, Bjorn Andersson, Konrad Dybcio,
Peter Griffin, Alim Akhtar
Cc: linux-kernel, devicetree, linux-arm-msm, linux-arm-kernel,
linux-samsung-soc, Krzysztof Kozlowski
Ignore redundant whitespaces in a few places to suppress warnings from
`dt-check-style --mode relaxed` like:
sc7280-herobrine.dtsi:357: [redundant-whitespace] extra whitespace after :
Signed-off-by: Krzysztof Kozlowski <krzysztof.kozlowski@oss.qualcomm.com>
---
arch/arm64/boot/dts/qcom/sc7280-herobrine.dtsi | 6 ++++++
arch/arm64/boot/dts/qcom/sm8750.dtsi | 4 ++++
2 files changed, 10 insertions(+)
diff --git a/arch/arm64/boot/dts/qcom/sc7280-herobrine.dtsi b/arch/arm64/boot/dts/qcom/sc7280-herobrine.dtsi
index 58ea0532c0fb..21179ca1219b 100644
--- a/arch/arm64/boot/dts/qcom/sc7280-herobrine.dtsi
+++ b/arch/arm64/boot/dts/qcom/sc7280-herobrine.dtsi
@@ -354,11 +354,13 @@ keyboard_backlight: led-0 {
pp1256_s8b: &vreg_s8b_1p256 {};
pp1800_l18b_s0: &vreg_l18b_1p8 {};
+/* dt-check-style disable=redundant-whitespace */
pp1800_l18b: &vreg_l18b_1p8 {};
vreg_l19b_s0: &vreg_l19b_1p8 {};
pp1800_alc5682: &vreg_l2c_1p8 {};
+/* dt-check-style disable=redundant-whitespace */
pp1800_l2c: &vreg_l2c_1p8 {};
vreg_l4c: &vreg_l4c_1p8_3p0 {};
@@ -368,14 +370,17 @@ keyboard_backlight: led-0 {
pp3000_l7c: &vreg_l7c_3p0 {};
pp1800_prox: &vreg_l8c_1p8 {};
+/* dt-check-style disable=redundant-whitespace */
pp1800_l8c: &vreg_l8c_1p8 {};
pp2950_l9c: &vreg_l9c_2p96 {};
+/* dt-check-style disable=redundant-whitespace */
pp1800_lcm: &vreg_l12c_1p8 {};
pp1800_mipi: &vreg_l12c_1p8 {};
pp1800_l12c: &vreg_l12c_1p8 {};
+/* dt-check-style disable=redundant-whitespace */
pp3300_lcm: &vreg_l13c_3p0 {};
pp3300_mipi: &vreg_l13c_3p0 {};
pp3300_l13c: &vreg_l13c_3p0 {};
@@ -384,6 +389,7 @@ keyboard_backlight: led-0 {
vreg_edp_bl: &ppvar_sys {};
+/* dt-check-style disable=redundant-whitespace */
ts_avdd: &pp3300_left_in_mlb {};
vreg_edp_3p3: &pp3300_left_in_mlb {};
diff --git a/arch/arm64/boot/dts/qcom/sm8750.dtsi b/arch/arm64/boot/dts/qcom/sm8750.dtsi
index ed3d29e13021..afeb6e57e0aa 100644
--- a/arch/arm64/boot/dts/qcom/sm8750.dtsi
+++ b/arch/arm64/boot/dts/qcom/sm8750.dtsi
@@ -2480,6 +2480,7 @@ swr3: soundwire@6ab0000 {
qcom,din-ports = <4>;
qcom,dout-ports = <9>;
+ /* dt-check-style disable=redundant-whitespace-strict */
qcom,ports-sinterval = /bits/ 16 <0x07 0x1f 0x3f 0x07 0x1f 0x3f 0x18f 0x18f 0x18f 0x0f 0x0f 0xff 0x31f>;
qcom,ports-offset1 = /bits/ 8 <0x01 0x03 0x05 0x02 0x04 0x15 0x00 0x00 0x00 0x06 0x0d 0xff 0x00>;
qcom,ports-offset2 = /bits/ 8 <0xff 0x07 0x1f 0xff 0x07 0x1f 0xff 0xff 0xff 0xff 0xff 0xff 0xff>;
@@ -2527,6 +2528,7 @@ swr1: soundwire@6ad0000 {
qcom,din-ports = <1>;
qcom,dout-ports = <11>;
+ /* dt-check-style disable=redundant-whitespace-strict */
qcom,ports-sinterval = /bits/ 16 <0x03 0x3f 0x1f 0x07 0x00 0x18f 0xff 0xff 0x31 0xff 0xff 0xff>;
qcom,ports-offset1 = /bits/ 8 <0x00 0x00 0x0b 0x01 0x00 0x00 0xff 0xff 0x00 0xff 0xff 0xff>;
qcom,ports-offset2 = /bits/ 8 <0x00 0x00 0x0b 0x00 0x00 0x00 0xff 0xff 0x00 0xff 0xff 0xff>;
@@ -2591,6 +2593,7 @@ swr0: soundwire@6b10000 {
qcom,din-ports = <4>;
qcom,dout-ports = <9>;
+ /* dt-check-style disable=redundant-whitespace-strict */
qcom,ports-sinterval = /bits/ 16 <0x07 0x1f 0x3f 0x07 0x1f 0x3f 0x18f 0x18f 0x18f 0x0f 0x0f 0xff 0x31f>;
qcom,ports-offset1 = /bits/ 8 <0x01 0x03 0x05 0x02 0x04 0x15 0x00 0x00 0x00 0x06 0x0d 0xff 0x00>;
qcom,ports-offset2 = /bits/ 8 <0xff 0x07 0x1f 0xff 0x07 0x1f 0xff 0xff 0xff 0xff 0xff 0xff 0xff>;
@@ -2644,6 +2647,7 @@ swr2: soundwire@7630000 {
qcom,din-ports = <4>;
qcom,dout-ports = <0>;
+ /* dt-check-style disable=redundant-whitespace-strict */
qcom,ports-sinterval-low = /bits/ 8 <0x01 0x01 0x03 0x03>;
qcom,ports-offset1 = /bits/ 8 <0x00 0x00 0x01 0x01>;
qcom,ports-offset2 = /bits/ 8 <0x00 0x00 0x00 0x00>;
--
2.53.0
^ permalink raw reply [flat|nested] 5+ messages in thread