Policy

Git Work Flow

Version Numbering

Each release of XCSoar is denoted by a unique version number. A version number consists three sequential numerical fields separated a period and prefixed by a v. The significance of the three fields are <major>.<minor>.<patch>. So, for instance, the version number v7.1.3 indicates XCSoar major version 7, minor version 1, and patch 3.

Release versions are determined and maintained by the release manager.

Git Repository Enduring Branches

At any time the XCSoar contains two enduring branches. The principle enduring branch is ’master’. The lifetime of this branch is unbounded. The second enduring branch is the current minor version branch. The lifetime of this branch is the lifetime of the current minor version. The name of the minor version branch is in the form ’v<major>.<minor>.x’ So, for instance, the current minor branch may be called ’v7.1.x’.

With the commencement of a new minor version the release manager will create the required branch. The old minor branch will be retired. All XCSoar releases are made from the current minor branch.

The master branch serves as the development branch for the next minor release (which may also be the first minor of the next major release).

Developers should commit changes for the next minor release to the master branch. Bug fixes of the current minor release should be committed to the current minor branch, in preparation for the next patch release.

Writing Patches

There are two methods to summit patches to the upstream XCSoar repository.

GitHub

The XCSoar repository is currently hosted at XCSoar GitHub repository. GitHub provides a method for submitting patches using their Web interface. The easiest way to use this method is to make another XCSoar repository by ’forking’ from ’XCSoar/XCSoar’. Make sure that your local repository is up to date with the upstream XCSoar/XCSoar repository. Then make a feature branch from the master or current minor branch as appropriate for the change you are making and commit the changes to that branch. To make the upstream merge easier it is best to re base this feature branch with the appropriate upstream branch from time to time.

When ready to submit the feature branch to the upstream push your local repository to your GitHub XCSoar repository and use the GitHub Web interface to make a “pull request” of your feature branch to XCSoar/XCSoar.

Developers’ Mail List

The second method is to submit patches or git pull requests to the developer mailing list (xcsoar-devel@lists.sourceforge.net).

Patch files can be generated by running:

git diff > patch

Basic Patch Requirements

A patch should be self-explanatory, it needs a good description. The subject line specifies the subsystem/library name and a brief description of what is changed, followed by an empty line. Then write a longer description if needed, and explain why this change is needed.

Each patch must compile and must not introduce a regression (as far as we know at the time).

Each patch must be self-contained and should only change one thing. Split larger patches into smaller pieces. Don’t refactor and add/modify/remove features in the same patch.

Don’t rewrite code unless you need to. Migrate incrementally to a new concept. Keep patches small and easy to understand.

Code Style

79 columns, reasonable exceptions allowed. Indent 2 spaces, no tabs. No indent for namespace blocks (a compromise to avoid excessive indentation).

Comments: write enough code comments (in English). All workarounds must be documented. Everybody must be able to understand your code, even when you’re gone. Don’t abuse multiple single-line comments (//) to write mult-line comments.

API documentation: non-trivial functions should be documented in a doxygen comment.

Names: class/function names in CamelCase (not camelCase); attributes/variables lower case, separated with underscore (e.g. foo_bar); constants (including enum values) all upper case (e.g. FOO_BAR).

Exception: when a foreign API is being mimicked (e.g. STL containers), we adopt its naming conventions.

Files: *.cpp and *.hpp for C++. Files should be named after the main class which is provided. Each class should have a separate source file and a separate header. UNIX text format.

Be const-correct. Use constexpr instead of const whenever possible.

Use static whenever possible. Functions and global variables that are only used in one source file should not be exported. Methods that do not use any instance method/variable should be static to avoid the overhead of passing the implicit this parameter.

Make methods virtual only after careful consideration. A destructor should only be virtual if necessary. All overrides must use the override keyword. Use final often.

Compile with WERROR=y and fix all warnings.

Don’t write large functions. Split them up when they become too large.

Avoid dynamic allocation. Dynamic allocation means overhead, more locking and heap fragmentation. Use StaticArray and StaticString if possible.

Asterisks belong to the variable name, not to the type name. Consider Foo* a, b. Foo *a, b or Foo *a, *b is easier to understand.

Some sample code to demonstrate our code style:

/**
 * API documentation for this class.
 */
struct TheStruct {
  unsigned an_attribute;
  bool second_attribute;

  TheStruct();

  /**
   * API documentation for this method.
   *
   * @param foo documentation for this parameter
   * @return documentation for the return value
   */
  bool TheMethod(int foo);
};

TheStruct::TheStruct()
  :an_attribute(0),
   second_attribute(true)
{
}

static bool
FooBar(int a_parameter, unsigned another_parameter,
       const TheStruct *next_row)
{
  switch (a_parameter) {
  case 0:
    break;
  }

  if (a_parameter == 2 && another_parameter == 3 &&
      next_row != NULL)
    return true;

  return a_parameter == 42;
}

C++

XCSoar is written in C++20.

XCSoar’s standard compilers are gcc (at least version 10) and clang (at least version 12).

Avoid preprocessor macros, because they are obscure, error prone, not type-safe, hard to read and hard to debug. Use inline functions and constexpr variables instead.

Other rules

In a class declaration, attributes come first, then constructor/destructor, and finally the methods. Having all attributes in one place gives a good overview of the nature of a class.

Avoid expensive and bloated STL containers if there are cheaper solutions (e.g. StaticArray, StaticString if the maximum size is predictable).

Avoid template hell. Keep templates readable. Keep in mind that excessive template use may bloat the binary.

Graphical User Interface

Letter Cases

Following the guidline should prevent the GUI from mixtures of “ON” and “On” text elements, and lead to a systematic GUI text presentation. The goal is to recognize GUI text fast and reliable.

Captions

Captions (button captions, windows titles) to use capitalization. E.g. ,“Pan On”, “The Display Of …”.

Abbreviations

Generally known abbreviation use upper case like “MC”, “ETA”, “V”; or they can use CamelCase, especially when using synthetic words like “GoTo”, “InfoBox”. Abbreviated words by simply cutting the end of the word needs a dot, e.g. “Max. temp.”

Plain text

Longer help texts are to write like prose: “This is the help page for …”.

Labels

Label text has the least systematic constraints:

  • Captions for text (input) fields, e.g. “Wing loading”

  • Info text on widgets. E.g. “No data” on an empty analysis page.

  • Label text for radio or check boxes.

  • Selections on Combo-boxes, selectors, Pull-down menus.

All those should go like prose, whereas exceptions might be meaningful.

Gauge caption

Also the appearance of the gauge caption should be covered with that. They are currently mapped to upper case all over. I think the most readable also here is a CamelCase approach. E.g. to distinct “WP Dist”, “WP AltD”, and “WP AltR”. Another good example would be MACCREADY, which should be MacCready, or just MC.

Units

Units have their own specific appearance. A profound paper is http://physics.nist.gov/cuu/pdf/checklist.pdf we could just refer to.