Code conventions for the build system
kumar.x.srinivasan at oracle.com
Wed Dec 18 18:08:18 UTC 2013
Is this formalized some place ? If not it would be good to get this
posted on a wiki or at http://openjdk.java.net/groups/build/
On 10/8/2013 12:40 AM, Magnus Ihse Bursie wrote:
> Whitespace and indentation in makefiles is a more problematic area
> than for other languages. Even while most of the time whitespace is
> not significant, sometimes is is. This might be considered a design
> flaw in make, but that's not something we can do anything about. In
> particular, initial tabs signify make rule recipes, and in make string
> manipulation, sometimes spaces matter.
> Probably partly due to this, there is little editor/IDE/tooling
> support for automatically formatting makefiles. This in turns makes
> keeping sane whitespace usage and indentation a "manual" task. When we
> started writing the new build system, we didn't set up a set of coding
> conventions to regulate whitespace and indentation (which we regret
> now). So the existing code varies wildly in style and indentation. All
> too often, proper indentation is completely missing, making it hard to
> read and understand the code.
> So, we created a set of rules for indention and whitespace usage. We
> tried to stay close to the Java code conventions, but Makefiles are
> not Java source code. We have then started to transform the code base
> according to these conventions. A webrev will shortly follow, with the
> whitespace changes resulting from this work.
> But first, let us present the set of rules.
> 1) The basic level of indentation is two spaces. Use this for
> "logical" indentation (if blocks, function definitions etc).
> 2) If a line must be broken, use four spaces for indentation.
> 3) Recipes in makefile rules must start with a tab (per definition).
> 4) If a single tab (interpreted as 8 spaces wide) is not enough to
> put the recipe clearly indented (meaning at least 4 spaces difference)
> from the code around it, use additional tabs.
> 5) Non-shell commands in a recipe (e.g. comments and make directives
> like ifdef) must not start with tab, but should instead be indented to
> the same level as the surrounding shell commands using spaces (with
> tabs interpreted as 8 spaces wide).
> 6) Additional indentation in recipes should be done using space
> after the tab(s), as in normal makefile lines.
> 7) Partial recipes (macro definitions that are supposed to be
> inlined into a recipe) should be treaded like a recipe and start with
> tabs as well.
> Whitespace, required:
> 8) Trailing whitespaces is never allowed.
> 9) Do not use tabs, only spaces (except for in recipes, as stated by
> rule 3-7).
> Whitespace, recommended:
> 10) There should be no whitespace between the list of targets and the
> : at the start of a rule.
> 11) There should be an empty line before and after each rule.
> 12) Avoid empty lines inside the recipe.
> 13) Broken lines should end with a backslash, and a single space
> before the backslash (" \").
> 14) A single space should separate a comma from the next argument in
> a function call.
> 15) A single space should be used before and after assignment
> operators (e.g. :=, =, +=).
> These recommendations are not always possible to follow, since
> whitespace might have semantic meaning. If an exception from these
> recommendations is required by make, it should ideally be pointed out
> by a comment. Especially spacing around commas might be sensitive, so
> Style recommentations:
> 16) Use := (direct assignment) instead of = (recursive macro
> definition), unless you really need the recursive definition.
> 17) In long lists, do not let the first and last element have
> different form. For instance, start the first element on a new line
> rather than after a :=, and end the list with an empty comment (#) to
> be able to have a trailing backslash on the last line.
> 18) Avoid padding internally in a line with spaces to try to align
> some feature into columns with surrounding lines.
> 19) For multiple commands run by the shell, separated by "&& \" or
> similar, all commands should start at the same indention level.
> Rationales (to some of the rules):
> 1-2) This is in contrast to Java, which has twice as long
> indentations (4 space logical indentation, 8 spaces for wrapped
> lines). But since all indentation needs to be done basically by
> repeatedly pressing space, and since wrapped lines are fairly common,
> we felt it important to keep the indentation level short. Otherwise a
> wrapped line two levels in would needed 16 presses on the space bar.
> 9-12) Tabs are required in recipes, but for the sake of sanity, this
> is the only accepted use of tabs. The makefile syntax does not make it
> easy to spot rules in complex makefiles, and everything that helps in
> distinguishing rules from non-rules is needed.
> 16) Recursive macro definition (= instead of :=) slows down make and
> can have surprising effects. Typically this is not what you mean.
> 17-18) A very typical use case of makefile changes is to add things
> (files, compiler directives, etc) to a list. These rules help making
> such changes easy and context free. Otherwise the developer must
> modify several lines that are unrelated to the actual change. Chances
> are that a nicely padded grid will not be updated and start
> deteriorating from the very first change.
> 19) Separating multiple shell commands (e.g. after a shell "if"
> command) should not be considered a broken line which needs to be
> indenting, but a way to specify a list of commands on the same
> indentation levels. This is after all the intent; the && is merely a
> roundabout device to get this to work properly in makefiles.
More information about the build-dev