lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite for Android: free password hash cracker in your pocket
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <20250509203430.3448-7-adobriyan@gmail.com>
Date: Fri,  9 May 2025 23:34:28 +0300
From: Alexey Dobriyan <adobriyan@...il.com>
To: corbet@....net
Cc: workflows@...r.kernel.org,
	linux-kernel@...r.kernel.org,
	Alexey Dobriyan <adobriyan@...il.com>
Subject: [PATCH 7/9] CodingStyle: new variable declaration placement rule

Linux finally compiles without -Wdeclaration-after-statement allowing
to declare variables anywhere in the code.

The rule is that variable is declared as late as possible:

1) it is possible to typo a variable and use by mistake between
   declaration and first legitimate use.

   Declaring variable later decreases this risk.

2) it is possible to typo variable between last legitimate use and
   the end of the scope.

   Declaring variable in the innermost scope decreases this risk.

3) declaring ALAP (as late as possible) often allows to merge declaration
   and assignment into declaration with initializer. This saves LOC
   without readability loss.

4) declaring ALAP allows to use "const" on the variable if necessary.

   Linux doesn't use "const" much outside of "const T*" but with
   split declaration/assignment it is not possible at all.

4) declaring lower naturally breaks some misguided rules (I'm being
   polite here) about declarations: there is a rule saying that
   declaration block in the beginning of the scope must be sorted
   by length forming trapezoid-like shape

   	XXXXXXXXXXXXXXXXXXXXX
	XXXXXXXXXXXXXXXXXXX
	XXXXXXXXXXX
	XXXXXXXXX
	int rv;

   so the code looks nicer (allegedly). This is misguided (still polite)
   because code is formatted not for of objectively good characteristics
   (bug risk, codegen quality, easy of maintainance) but for subjective
   qualities like being aesthetically pleasing to look at.

5) K&R rule about declaring variables in the beginning of the scope is
   pointless restriction. It is very obvious after programming something
   other than C. All popular programming languages either never had K&R
   rule or discarded it at some point implying that even if it was
   useful (it wasn't), it was so marginally useful that everyone thought
   it is not worth it.

This patch makes 100% of the code non-compliant, but, oh well...

Signed-off-by: Alexey Dobriyan <adobriyan@...il.com>
---
 Documentation/process/coding-style.rst | 72 ++++++++++++++++++++++++++
 1 file changed, 72 insertions(+)

diff --git a/Documentation/process/coding-style.rst b/Documentation/process/coding-style.rst
index f8d5151eb0d2..e17de69845ff 100644
--- a/Documentation/process/coding-style.rst
+++ b/Documentation/process/coding-style.rst
@@ -95,6 +95,78 @@ used for indentation, and the above example is deliberately broken.
 Get a decent editor and don't leave whitespace at the end of lines.
 
 
+Variable declarations
+---------------------
+
+Each variable is declared in the innermost scope possible
+where ``for`` initialization clause counts as a scope as well.
+
+Inside specific scope each variable is declared as late as possible as if
+declarations have "mass" and "fall down":
+
+.. code-block:: c
+
+	int f(void *priv)
+	{
+		struct xxx_obj *obj = to_xxx_obj(priv);
+
+		rcu_read_lock();
+		int s_xxx = 0;
+		for (int i = 0; i < n_xxx; i++) {
+			s_xxx += obj->xxx[i];
+		}
+		rcu_read_unlock();
+
+		unsigned long flags;
+		spin_lock_irqsave(&obj->lock, &flags);
+		int rv = obj_make(obj, s_xxx);
+		spin_unlock_irqrestore(&obj->lock, &flags);
+		return rv;
+	}
+
+
+These rules minimise a) the risk of variable misuse between declaration and
+first legitimate use, b) allow to transform declaration and first assignment
+into declaration with initializer saving LOC on average without readability
+loss and c) allow to use ``const`` if necessary:
+
+.. code-block:: c
+
+	T a;
+	T b;
+
+	a = g();/* bug, should be "b = " */
+
+	a = f();
+
+		vs
+
+	T b;
+	a = g(); /* compile error */
+	[const] T a = f(); /* OK */
+
+Each declaration is put on its own line:
+
+.. code-block:: c
+
+	T a = ...;
+	T tmp;
+
+C allows to declare multiple variables in the same statement but it is
+a misfeature. It leads to confusion if pointers are involved, even more
+confusion and long lines with initializers (likely going above character
+limit) and avoidable changes in patches.
+
+Very long declarations are split after the ``=`` character:
+
+.. code-block:: c
+
+	struct xxx_obj *obj =
+		xxx_obj_alloc(Long, list, of, arguments);
+
+Most of the time both lines fit just fine into the character limit afterwards.
+
+
 Breaking long lines and strings
 -------------------------------
 
-- 
2.49.0


Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ