1.. _docs-pw-style-cpp: 2 3========= 4C++ style 5========= 6The Pigweed C++ style guide is closely based on Google's external C++ Style 7Guide, which is found on the web at 8https://google.github.io/styleguide/cppguide.html. The Google C++ Style Guide 9applies to Pigweed except as described in this document. 10 11The Pigweed style guide only applies to Pigweed itself. It does not apply to 12projects that use Pigweed or to the third-party code included with Pigweed. 13Non-Pigweed code is free to use features restricted by Pigweed, such as dynamic 14memory allocation and the entirety of the C++ Standard Library. 15 16Recommendations in the :ref:`docs-embedded-cpp` are considered part of the 17Pigweed style guide, but are separated out since it covers more general 18embedded development beyond just C++ style. 19 20C++ standard 21============ 22All Pigweed C++ code must compile with ``-std=c++17`` in Clang and GCC. C++20 23features may be used as long as the code still compiles unmodified with C++17. 24See ``pw_polyfill/language_feature_macros.h`` for macros that provide C++20 25features when supported. 26 27Compiler extensions should not be used unless wrapped in a macro or properly 28guarded in the preprocessor. See ``pw_processor/compiler.h`` for macros that 29wrap compiler-specific features. 30 31Automatic formatting 32==================== 33Pigweed uses `clang-format <https://clang.llvm.org/docs/ClangFormat.html>`_ to 34automatically format Pigweed source code. A ``.clang-format`` configuration is 35provided with the Pigweed repository. Within an upstream Pigweed environment, the 36`pw format` tool can be used to automatically format code. 37 38Automatic formatting is essential to facilitate large-scale, automated changes 39in Pigweed. Therefore, all code in Pigweed is expected to be formatted with 40``clang-format`` prior to submission. Existing code may be reformatted at any 41time. 42 43If ``clang-format`` formats code in an undesirable or incorrect way, it can be 44disabled for the affected lines by adding ``// clang-format off``. 45``clang-format`` must then be re-enabled with a ``// clang-format on`` comment. 46 47.. code-block:: cpp 48 49 // clang-format off 50 constexpr int kMyMatrix[] = { 51 100, 23, 0, 52 0, 542, 38, 53 1, 2, 201, 54 }; 55 // clang-format on 56 57C Standard Library 58================== 59In C++ headers, always use the C++ versions of C Standard Library headers (e.g. 60``<cstdlib>`` instead of ``<stdlib.h>``). If the header is used by both C and 61C++ code, only the C header should be used. 62 63In C++ code, it is preferred to use C functions from the ``std`` namespace. For 64example, use ``std::memcpy`` instead of ``memcpy``. The C++ standard does not 65require the global namespace versions of the functions to be provided. Using 66``std::`` is more consistent with the C++ Standard Library and makes it easier 67to distinguish Pigweed functions from library functions. 68 69Within core Pigweed, do not use C standard library functions that allocate 70memory, such as ``std::malloc``. There are exceptions to this for when dynamic 71allocation is enabled for a system; Pigweed modules are allowed to add extra 72functionality when a heap is present; but this must be optional. 73 74C++ Standard Library 75==================== 76Much of the C++ Standard Library is not a good fit for embedded software. Many 77of the classes and functions were not designed with the RAM, flash, and 78performance constraints of a microcontroller in mind. For example, simply 79adding the line ``#include <iostream>`` can increase the binary size by 150 KB! 80This is larger than many microcontrollers' entire internal storage. 81 82However, with appropriate caution, a limited set of standard C++ libraries can 83be used to great effect. Developers can leverage familiar, well-tested 84abstractions instead of writing their own. C++ library algorithms and classes 85can give equivalent or better performance than hand-written C code. 86 87A limited subset of the C++ Standard Library is permitted in Pigweed. To keep 88Pigweed small, flexible, and portable, functions that allocate dynamic memory 89must be avoided. Care must be exercised when using multiple instantiations of a 90template function, which can lead to code bloat. 91 92Permitted Headers 93----------------- 94.. admonition:: The following C++ Standard Library headers are always permitted: 95 :class: checkmark 96 97 * ``<array>`` 98 * ``<complex>`` 99 * ``<initializer_list>`` 100 * ``<iterator>`` 101 * ``<limits>`` 102 * ``<optional>`` 103 * ``<random>`` 104 * ``<ratio>`` 105 * ``<string_view>`` 106 * ``<tuple>`` 107 * ``<type_traits>`` 108 * ``<utility>`` 109 * ``<variant>`` 110 * C Standard Library headers (``<c*>``) 111 112.. admonition:: With caution, parts of the following headers can be used: 113 :class: warning 114 115 * ``<algorithm>`` -- be wary of potential memory allocation 116 * ``<atomic>`` -- not all MCUs natively support atomic operations 117 * ``<bitset>`` -- conversions to or from strings are disallowed 118 * ``<functional>`` -- do **not** use ``std::function``; use 119 :ref:`module-pw_function` 120 * ``<mutex>`` -- can use ``std::lock_guard``, use :ref:`module-pw_sync` for 121 mutexes 122 * ``<new>`` -- for placement new 123 * ``<numeric>`` -- be wary of code size with multiple template instantiations 124 125.. admonition:: Never use any of these headers: 126 :class: error 127 128 * Dynamic containers (``<list>``, ``<map>``, ``<set>``, ``<vector>``, etc.) 129 * Streams (``<iostream>``, ``<ostream>``, ``<fstream>``, ``<sstream>`` etc.) 130 -- in some cases :ref:`module-pw_stream` can work instead 131 * ``<span>`` -- use :ref:`module-pw_span` instead. Downstream projects may 132 want to directly use ``std::span`` if it is available, but upstream must 133 use the ``pw::span`` version for compatability 134 * ``<string>`` -- can use :ref:`module-pw_string` 135 * ``<thread>`` -- can use :ref:`module-pw_thread` 136 * ``<future>`` -- eventually :ref:`module-pw_async` will offer this 137 * ``<exception>``, ``<stdexcept>`` -- no exceptions 138 * ``<memory>``, ``<scoped_allocator>`` -- no allocations 139 * ``<regex>`` 140 * ``<valarray>`` 141 142Headers not listed here should be carefully evaluated before they are used. 143 144These restrictions do not apply to third party code or to projects that use 145Pigweed. 146 147Combining C and C++ 148=================== 149Prefer to write C++ code over C code, using ``extern "C"`` for symbols that must 150have C linkage. ``extern "C"`` functions should be defined within C++ 151namespaces to simplify referring to other code. 152 153C++ functions with no parameters do not include ``void`` in the parameter list. 154C functions with no parameters must include ``void``. 155 156.. code-block:: cpp 157 158 namespace pw { 159 160 bool ThisIsACppFunction() { return true; } 161 162 extern "C" int pw_ThisIsACFunction(void) { return -1; } 163 164 extern "C" { 165 166 int pw_ThisIsAlsoACFunction(void) { 167 return ThisIsACppFunction() ? 100 : 0; 168 } 169 170 } // extern "C" 171 172 } // namespace pw 173 174Comments 175======== 176Prefer C++-style (``//``) comments over C-style comments (``/* */``). C-style 177comments should only be used for inline comments. 178 179.. code-block:: cpp 180 181 // Use C++-style comments, except where C-style comments are necessary. 182 // This returns a random number using an algorithm I found on the internet. 183 #define RANDOM_NUMBER() [] { \ 184 return 4; /* chosen by fair dice roll */ \ 185 }() 186 187Indent code in comments with two additional spaces, making a total of three 188spaces after the ``//``. All code blocks must begin and end with an empty 189comment line, even if the blank comment line is the last line in the block. 190 191.. code-block:: cpp 192 193 // Here is an example of code in comments. 194 // 195 // int indentation_spaces = 2; 196 // int total_spaces = 3; 197 // 198 // engine_1.thrust = RANDOM_NUMBER() * indentation_spaces + total_spaces; 199 // 200 bool SomeFunction(); 201 202Passing move-only or expensive-to-copy arguments 203================================================ 204C++ offers a number of ways to pass arguments arguments to functions. 205When taking move-only or expensive-to-copy arguments, use the following table 206to determine which argument type to use: 207 208.. list-table:: C++ argument type choices 209 :widths: 30 20 10 210 :header-rows: 1 211 212 * - Use-case 213 - Name 214 - Syntax 215 * - If read-only 216 - By const reference 217 - ``const T&`` 218 * - If mutating 219 - By reference 220 - ``T&`` 221 * - If consuming 222 - By rvalue reference 223 - ``T&&`` 224 * - If conditionally consuming 225 - By value 226 - ``T`` 227 228Why rvalue references 229--------------------- 230When a function consumes or moves such an argument, it should accept an rvalue 231reference (``T&&``) rather than taking the argument by-value (``T``). An rvalue 232reference forces the caller to ``std::move`` when passing a preexisting 233variable, which makes the transfer of ownership explicit. 234 235Compared with accepting arguments by-value, rvalue references prevent 236unnecessary object instances and extra calls to move constructors. This has been 237shown to significantly impact code size and stack usage for Pigweed users. 238 239This is especially important when using ``pw::Function``. For more information 240about accepting ``pw::Function`` arguments, see 241:ref:`module-pw_function-move-semantics`. 242 243.. admonition:: **Yes**: Accept move-only or expensive-to-copy values by rvalue: 244 :class: checkmark 245 246 .. code-block:: cpp 247 248 void FrobulateVector(pw::Vector<T>&& vector) { 249 Frobulate(std::move(vector)); 250 } 251 252.. admonition:: **No**: Accepts move-only or expensive-to-copy values by value: 253 :class: error 254 255 .. code-block:: cpp 256 257 void FrobulateVector(pw::Vector<T> vector) { 258 Frobulate(std::move(vector)); 259 } 260 261This guidance overrides the standard `Google style guidance on rvalues 262<https://google.github.io/styleguide/cppguide.html#Rvalue_references>`_. 263 264Conditionally moving values 265--------------------------- 266An exception to the rule above is when a move-only or expensive-to-copy value 267is only conditionally consumed by the body of the function, for example: 268 269.. admonition:: **No**: Conditionally consumes ``vector``: 270 :class: error 271 272 .. code-block:: cpp 273 274 void PossiblyFrobulate(bool should_frob, pw::Vector<T>&& vector) { 275 if (should_frob) { 276 Frobulate(std::move(vector)); 277 } 278 } 279 280Because ``PossiblyFrobulate`` above will only consume ``vector`` in some code 281paths, the original ``vector`` passed by the user will outlive the call to 282``PossiblyFrobulate``: 283 284.. code-block:: cpp 285 286 pw::Vector<T> my_vec = ...; 287 288 // ``my_vec`` looks to be moved here, but the resulting ``rvalue`` is never 289 // consumed by ``PossiblyFrobulate``. 290 PossiblyFrobulate(false, std::move(my_vec)); 291 292 ... // some other long-running work 293 294 // ``my_vec`` is still alive here, possibly causing excess memory usage, 295 // deadlocks, or even undefined behavior! 296 297When conditionally consuming an argument, prefer instead to either accept 298the argument by-value or ensure that it is consumed by all control paths: 299 300.. admonition:: **Yes**: Conditionally consumes by-value ``vector``: 301 :class: checkmark 302 303 .. code-block:: cpp 304 305 void PossiblyFrobulate(bool should_frob, pw::Vector<T> vector) { 306 if (should_frob) { 307 Frobulate(std::move(vector)); 308 } 309 } 310 311.. admonition:: **Yes**: Consumes ``vector`` on all control paths: 312 :class: checkmark 313 314 .. code-block:: cpp 315 316 void PossiblyFrobulate(bool should_frob, pw::Vector<T>&& vector) { 317 if (should_frob) { 318 Frobulate(std::move(vector)); 319 } else { 320 [[maybe_unused]] auto to_discard = std::move(vector); 321 } 322 } 323 324Control statements 325================== 326 327Loops and conditionals 328---------------------- 329All loops and conditional statements must use braces, and be on their own line. 330 331.. admonition:: **Yes**: Always use braces for line conditionals and loops: 332 :class: checkmark 333 334 .. code-block:: cpp 335 336 while (SomeCondition()) { 337 x += 2; 338 } 339 if (OtherCondition()) { 340 DoTheThing(); 341 } 342 343 344.. admonition:: **No**: Missing braces 345 :class: error 346 347 .. code-block:: cpp 348 349 while (SomeCondition()) 350 x += 2; 351 if (OtherCondition()) 352 DoTheThing(); 353 354.. admonition:: **No**: Statement on same line as condition 355 :class: error 356 357 .. code-block:: cpp 358 359 while (SomeCondition()) { x += 2; } 360 if (OtherCondition()) { DoTheThing(); } 361 362 363The syntax ``while (true)`` is preferred over ``for (;;)`` for infinite loops. 364 365.. admonition:: **Yes**: 366 :class: checkmark 367 368 .. code-block:: cpp 369 370 while (true) { 371 DoSomethingForever(); 372 } 373 374.. admonition:: **No**: 375 :class: error 376 377 .. code-block:: cpp 378 379 for (;;) { 380 DoSomethingForever(); 381 } 382 383 384Prefer early exit with ``return`` and ``continue`` 385-------------------------------------------------- 386Prefer to exit early from functions and loops to simplify code. This is the 387same same conventions as `LLVM 388<https://llvm.org/docs/CodingStandards.html#use-early-exits-and-continue-to-simplify-code>`_. 389We find this approach is superior to the "one return per function" style for a 390multitude of reasons: 391 392* **Visually**, the code is easier to follow, and takes less horizontal screen 393 space. 394* It makes it clear what part of the code is the **"main business" versus "edge 395 case handling"**. 396* For **functions**, parameter checking is in its own section at the top of the 397 function, rather than scattered around in the fuction body. 398* For **loops**, element checking is in its own section at the top of the loop, 399 rather than scattered around in the loop body. 400* Commit **deltas are simpler to follow** in code reviews; since adding a new 401 parameter check or loop element condition doesn't cause an indentation change 402 in the rest of the function. 403 404The guidance applies in two cases: 405 406* **Function early exit** - Early exits are for function parameter checking 407 and edge case checking at the top. The main functionality follows. 408* **Loop early exit** - Early exits in loops are for skipping an iteration 409 due to some edge case with an item getting iterated over. Loops may also 410 contain function exits, which should be structured the same way (see example 411 below). 412 413.. admonition:: **Yes**: Exit early from functions; keeping the main handling 414 at the bottom and de-dentend. 415 :class: checkmark 416 417 .. code-block:: cpp 418 419 Status DoSomething(Parameter parameter) { 420 // Parameter validation first; detecting incoming use errors. 421 PW_CHECK_INT_EQ(parameter.property(), 3, "Programmer error: frobnitz"); 422 423 // Error case: Not in correct state. 424 if (parameter.other() == MyEnum::kBrokenState) { 425 LOG_ERROR("Device in strange state: %s", parametr.state_str()); 426 return Status::InvalidPrecondition(); 427 } 428 429 // Error case: Not in low power mode; shouldn't do anything. 430 if (parameter.power() != MyEnum::kLowPower) { 431 LOG_ERROR("Not in low power mode"); 432 return Status::InvalidPrecondition(); 433 } 434 435 // Main business for the function here. 436 MainBody(); 437 MoreMainBodyStuff(); 438 } 439 440.. admonition:: **No**: Main body of function is buried and right creeping. 441 Even though this is shorter than the version preferred by Pigweed due to 442 factoring the return statement, the logical structure is less obvious. A 443 function in Pigweed containing **nested conditionals indicates that 444 something complicated is happening with the flow**; otherwise it would have 445 the early bail structure; so pay close attention. 446 :class: error 447 448 .. code-block:: cpp 449 450 Status DoSomething(Parameter parameter) { 451 // Parameter validation first; detecting incoming use errors. 452 PW_CHECK_INT_EQ(parameter.property(), 3, "Programmer error: frobnitz"); 453 454 // Error case: Not in correct state. 455 if (parameter.other() != MyEnum::kBrokenState) { 456 // Error case: Not in low power mode; shouldn't do anything. 457 if (parameter.power() == MyEnum::kLowPower) { 458 // Main business for the function here. 459 MainBody(); 460 MoreMainBodyStuff(); 461 } else { 462 LOG_ERROR("Not in low power mode"); 463 } 464 } else { 465 LOG_ERROR("Device in strange state: %s", parametr.state_str()); 466 } 467 return Status::InvalidPrecondition(); 468 } 469 470.. admonition:: **Yes**: Bail early from loops; keeping the main handling at 471 the bottom and de-dentend. 472 :class: checkmark 473 474 .. code-block:: cpp 475 476 for (int i = 0; i < LoopSize(); ++i) { 477 // Early skip of item based on edge condition. 478 if (!CommonCase()) { 479 continue; 480 } 481 // Early exit of function based on error case. 482 int my_measurement = GetSomeMeasurement(); 483 if (my_measurement < 10) { 484 LOG_ERROR("Found something strange; bailing"); 485 return Status::Unknown(); 486 } 487 488 // Main body of the loop. 489 ProcessItem(my_items[i], my_measurement); 490 ProcessItemMore(my_items[i], my_measurement, other_details); 491 ... 492 } 493 494.. admonition:: **No**: Right-creeping code with the main body buried inside 495 some nested conditional. This makes it harder to understand what is the 496 main purpose of the loop versus what is edge case handling. 497 :class: error 498 499 .. code-block:: cpp 500 501 for (int i = 0; i < LoopSize(); ++i) { 502 if (CommonCase()) { 503 int my_measurement = GetSomeMeasurement(); 504 if (my_measurement >= 10) { 505 // Main body of the loop. 506 ProcessItem(my_items[i], my_measurement); 507 ProcessItemMore(my_items[i], my_measurement, other_details); 508 ... 509 } else { 510 LOG_ERROR("Found something strange; bailing"); 511 return Status::Unknown(); 512 } 513 } 514 } 515 516There are cases where this structure doesn't work, and in those cases, it is 517fine to structure the code differently. 518 519No ``else`` after ``return`` or ``continue`` 520-------------------------------------------- 521Do not put unnecessary ``} else {`` blocks after blocks that terminate with a 522return, since this causes unnecessary rightward indentation creep. This 523guidance pairs with the preference for early exits to reduce code duplication 524and standardize loop/function structure. 525 526.. admonition:: **Yes**: No else after return or continue 527 :class: checkmark 528 529 .. code-block:: cpp 530 531 // Note lack of else block due to return. 532 if (Failure()) { 533 DoTheThing(); 534 return Status::ResourceExausted(); 535 } 536 537 // Note lack of else block due to continue. 538 while (MyCondition()) { 539 if (SomeEarlyBail()) { 540 continue; 541 } 542 // Main handling of item 543 ... 544 } 545 546 DoOtherThing(); 547 return OkStatus(); 548 549.. admonition:: **No**: Else after return needlessly creeps right 550 :class: error 551 552 .. code-block:: cpp 553 554 if (Failure()) { 555 DoTheThing(); 556 return Status::ResourceExausted(); 557 } else { 558 while (MyCondition()) { 559 if (SomeEarlyBail()) { 560 continue; 561 } else { 562 // Main handling of item 563 ... 564 } 565 } 566 DoOtherThing(); 567 return OkStatus(); 568 } 569 570Include guards 571============== 572The first non-comment line of every header file must be ``#pragma once``. Do 573not use traditional macro include guards. The ``#pragma once`` should come 574directly after the Pigweed copyright block, with no blank line, followed by a 575blank, like this: 576 577.. code-block:: cpp 578 579 // Copyright 2021 The Pigweed Authors 580 // 581 // Licensed under the Apache License, Version 2.0 (the "License"); you may not 582 // use this file except in compliance with the License. You may obtain a copy of 583 // the License at 584 // 585 // https://www.apache.org/licenses/LICENSE-2.0 586 // 587 // Unless required by applicable law or agreed to in writing, software 588 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 589 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 590 // License for the specific language governing permissions and limitations under 591 // the License. 592 #pragma once 593 594 // Header file-level comment goes here... 595 596Memory allocation 597================= 598Dynamic memory allocation can be problematic. Heap allocations and deallocations 599occupy valuable CPU cycles. Memory usage becomes nondeterministic, which can 600result in a system crashing without a clear culprit. 601 602To keep Pigweed portable, core Pigweed code is not permitted to dynamically 603(heap) allocate memory, such as with ``malloc`` or ``new``. All memory should be 604allocated with automatic (stack) or static (global) storage duration. Pigweed 605must not use C++ libraries that use dynamic allocation. 606 607Projects that use Pigweed are free to use dynamic allocation, provided they 608have selected a target that enables the heap. 609 610Naming 611====== 612Entities shall be named according to the `Google style guide 613<https://google.github.io/styleguide/cppguide.html>`_, with the following 614additional requirements. 615 616C++ code 617-------- 618* All Pigweed C++ code must be in the ``pw`` namespace. Namespaces for modules 619 should be nested under ``pw``. For example, ``pw::string::Format()``. 620* Whenever possible, private code should be in a source (.cc) file and placed in 621 anonymous namespace nested under ``pw``. 622* If private code must be exposed in a header file, it must be in a namespace 623 nested under ``pw``. The namespace may be named for its subsystem or use a 624 name that designates it as private, such as ``internal``. 625* Template arguments for non-type names (e.g. ``template <int kFooBar>``) should 626 follow the constexpr and const variable Google naming convention, which means 627 k prefixed camel case (e.g. ``kCamelCase``). This matches the Google C++ 628 style for variable naming, however the wording in the official style guide 629 isn't explicit for template arguments and could be interpreted to use 630 ``foo_bar`` style naming. For consistency with other variables whose value is 631 always fixed for the duration of the program, the naming convention is 632 ``kCamelCase``, and so that is the style we use in Pigweed. 633* Trivial membor accessors should be named with ``snake_case()``. The Google 634 C++ style allows either ``snake_case()`` or ``CapsCase()``, but Pigweed 635 always uses ``snake_case()``. 636* Abstract base classes should be named generically, with derived types named 637 specifically. For example, ``Stream`` is an abstract base, and 638 ``SocketStream`` and ``StdioStream`` are an implementations of that 639 interface. Any prefix or postfix indicating whether something is abstract or 640 concrete is not permitted; for example, ``IStream`` or ``SocketStreamImpl`` 641 are both not permitted. These pre-/post-fixes add additional visual noise and 642 are irrelevant to consumers of these interfaces. 643 644C code 645------ 646In general, C symbols should be prefixed with the module name. If the symbol is 647not associated with a module, use just ``pw`` as the module name. Facade 648backends may chose to prefix symbols with the facade's name to help reduce the 649length of the prefix. 650 651* Public names used by C code must be prefixed with the module name (e.g. 652 ``pw_tokenizer_*``). 653* If private code must be exposed in a header, private names used by C code must 654 be prefixed with an underscore followed by the module name (e.g. 655 ``_pw_assert_*``). 656* Avoid writing C source (.c) files in Pigweed. Prefer to write C++ code with C 657 linkage using ``extern "C"``. Within C source, private C functions and 658 variables must be named with the ``_pw_my_module_*`` prefix and should be 659 declared ``static`` whenever possible; for example, 660 ``_pw_my_module_MyPrivateFunction``. 661* The C prefix rules apply to 662 663 * C functions (``int pw_foo_FunctionName(void);``), 664 * variables used by C code (``int pw_foo_variable_name;``), 665 * constant variables used by C code (``const int pw_foo_kConstantName;``), 666 * structs used by C code (``typedef struct {} pw_foo_StructName;``), and 667 * all of the above for ``extern "C"`` names in C++ code. 668 669 The prefix does not apply to struct members, which use normal Google style. 670 671Preprocessor macros 672------------------- 673* Public Pigweed macros must be prefixed with the module name (e.g. 674 ``PW_MY_MODULE_*``). 675* Private Pigweed macros must be prefixed with an underscore followed by the 676 module name (e.g. ``_PW_MY_MODULE_*``). (This style may change, see 677 `b/234886184 <https://issuetracker.google.com/issues/234886184>`_). 678 679**Example** 680 681.. code-block:: cpp 682 683 namespace pw::my_module { 684 namespace nested_namespace { 685 686 // C++ names (types, variables, functions) must be in the pw namespace. 687 // They are named according to the Google style guide. 688 constexpr int kGlobalConstant = 123; 689 690 // Prefer using functions over extern global variables. 691 extern int global_variable; 692 693 class Class {}; 694 695 void Function(); 696 697 extern "C" { 698 699 // Public Pigweed code used from C must be prefixed with pw_. 700 extern const int pw_my_module_kGlobalConstant; 701 702 extern int pw_my_module_global_variable; 703 704 void pw_my_module_Function(void); 705 706 typedef struct { 707 int member_variable; 708 } pw_my_module_Struct; 709 710 // Private Pigweed code used from C must be prefixed with _pw_. 711 extern const int _pw_my_module_kPrivateGlobalConstant; 712 713 extern int _pw_my_module_private_global_variable; 714 715 void _pw_my_module_PrivateFunction(void); 716 717 typedef struct { 718 int member_variable; 719 } _pw_my_module_PrivateStruct; 720 721 } // extern "C" 722 723 // Public macros must be prefixed with PW_. 724 #define PW_MY_MODULE_PUBLIC_MACRO(arg) arg 725 726 // Private macros must be prefixed with _PW_. 727 #define _PW_MY_MODULE_PRIVATE_MACRO(arg) arg 728 729 } // namespace nested_namespace 730 } // namespace pw::my_module 731 732See :ref:`docs-pw-style-macros` for details about macro usage. 733 734Namespace scope formatting 735========================== 736All non-indented blocks (namespaces, ``extern "C"`` blocks, and preprocessor 737conditionals) must have a comment on their closing line with the 738contents of the starting line. 739 740All nested namespaces should be declared together with no blank lines between 741them. 742 743.. code-block:: cpp 744 745 #include "some/header.h" 746 747 namespace pw::nested { 748 namespace { 749 750 constexpr int kAnonConstantGoesHere = 0; 751 752 } // namespace 753 754 namespace other { 755 756 const char* SomeClass::yes = "no"; 757 758 bool ThisIsAFunction() { 759 #if PW_CONFIG_IS_SET 760 return true; 761 #else 762 return false; 763 #endif // PW_CONFIG_IS_SET 764 } 765 766 extern "C" { 767 768 const int pw_kSomeConstant = 10; 769 int pw_some_global_variable = 600; 770 771 void pw_CFunction() { ... } 772 773 } // extern "C" 774 775 } // namespace 776 } // namespace pw::nested 777 778Using directives for literals 779============================= 780`Using-directives 781<https://en.cppreference.com/w/cpp/language/namespace#Using-directives>`_ (e.g. 782``using namespace ...``) are permitted in implementation files only for the 783purposes of importing literals such as ``std::chrono_literals`` or 784``pw::bytes::unit_literals``. Namespaces that contain any symbols other than 785literals are not permitted in a using-directive. This guidance also has no 786impact on `using-declarations 787<https://en.cppreference.com/w/cpp/language/namespace#Using-declarations>`_ 788(e.g. ``using foo::Bar;``). 789 790Rationale: Literals improve code readability, making units clearer at the point 791of definition. 792 793.. code-block:: cpp 794 795 using namespace std::chrono; // Not allowed 796 using namespace std::literals::chrono_literals; // Allowed 797 798 constexpr std::chrono::duration delay = 250ms; 799 800Pointers and references 801======================= 802For pointer and reference types, place the asterisk or ampersand next to the 803type. 804 805.. code-block:: cpp 806 807 int* const number = &that_thing; 808 constexpr const char* kString = "theory!" 809 810 bool FindTheOneRing(const Region& where_to_look) { ... } 811 812Prefer storing references over storing pointers. Pointers are required when the 813pointer can change its target or may be ``nullptr``. Otherwise, a reference or 814const reference should be used. 815 816.. _docs-pw-style-macros: 817 818Preprocessor macros 819=================== 820Macros should only be used when they significantly improve upon the C++ code 821they replace. Macros should make code more readable, robust, and safe, or 822provide features not possible with standard C++, such as stringification, line 823number capturing, or conditional compilation. When possible, use C++ constructs 824like constexpr variables in place of macros. Never use macros as constants, 825except when a string literal is needed or the value must be used by C code. 826 827When macros are needed, the macros should be accompanied with extensive tests 828to ensure the macros are hard to use wrong. 829 830Stand-alone statement macros 831---------------------------- 832Macros that are standalone statements must require the caller to terminate the 833macro invocation with a semicolon (see `Swalling the Semicolon 834<https://gcc.gnu.org/onlinedocs/cpp/Swallowing-the-Semicolon.html>`_). For 835example, the following does *not* conform to Pigweed's macro style: 836 837.. code-block:: cpp 838 839 // BAD! Definition has built-in semicolon. 840 #define PW_LOG_IF_BAD(mj) \ 841 CallSomeFunction(mj); 842 843 // BAD! Compiles without error; semicolon is missing. 844 PW_LOG_IF_BAD("foo") 845 846Here's how to do this instead: 847 848.. code-block:: cpp 849 850 // GOOD; requires semicolon to compile. 851 #define PW_LOG_IF_BAD(mj) \ 852 CallSomeFunction(mj) 853 854 // GOOD; fails to compile due to lacking semicolon. 855 PW_LOG_IF_BAD("foo") 856 857For macros in function scope that do not already require a semicolon, the 858contents can be placed in a ``do { ... } while (0)`` loop. 859 860.. code-block:: cpp 861 862 #define PW_LOG_IF_BAD(mj) \ 863 do { \ 864 if (mj.Bad()) { \ 865 Log(#mj " is bad") \ 866 } \ 867 } while (0) 868 869Standalone macros at global scope that do not already require a semicolon can 870add a ``static_assert`` declaration statement as their last line. 871 872.. code-block:: cpp 873 874 #define PW_NEAT_THING(thing) \ 875 bool IsNeat_##thing() { return true; } \ 876 static_assert(true, "Macros must be terminated with a semicolon") 877 878Private macros in public headers 879-------------------------------- 880Private macros in public headers must be prefixed with ``_PW_``, even if they 881are undefined after use; this prevents collisions with downstream users. For 882example: 883 884.. code-block:: cpp 885 886 #define _PW_MY_SPECIAL_MACRO(op) ... 887 ... 888 // Code that uses _PW_MY_SPECIAL_MACRO() 889 ... 890 #undef _PW_MY_SPECIAL_MACRO 891 892Macros in private implementation files (.cc) 893-------------------------------------------- 894Macros within .cc files that should only be used within one file should be 895undefined after their last use; for example: 896 897.. code-block:: cpp 898 899 #define DEFINE_OPERATOR(op) \ 900 T operator ## op(T x, T y) { return x op y; } \ 901 static_assert(true, "Macros must be terminated with a semicolon") \ 902 903 DEFINE_OPERATOR(+); 904 DEFINE_OPERATOR(-); 905 DEFINE_OPERATOR(/); 906 DEFINE_OPERATOR(*); 907 908 #undef DEFINE_OPERATOR 909 910Preprocessor conditional statements 911=================================== 912When using macros for conditional compilation, prefer to use ``#if`` over 913``#ifdef``. This checks the value of the macro rather than whether it exists. 914 915* ``#if`` handles undefined macros equivalently to ``#ifdef``. Undefined 916 macros expand to 0 in preprocessor conditional statements. 917* ``#if`` evaluates false for macros defined as 0, while ``#ifdef`` evaluates 918 true. 919* Macros defined using compiler flags have a default value of 1 in GCC and 920 Clang, so they work equivalently for ``#if`` and ``#ifdef``. 921* Macros defined to an empty statement cause compile-time errors in ``#if`` 922 statements, which avoids ambiguity about how the macro should be used. 923 924All ``#endif`` statements should be commented with the expression from their 925corresponding ``#if``. Do not indent within preprocessor conditional statements. 926 927.. code-block:: cpp 928 929 #if USE_64_BIT_WORD 930 using Word = uint64_t; 931 #else 932 using Word = uint32_t; 933 #endif // USE_64_BIT_WORD 934 935Unsigned integers 936================= 937Unsigned integers are permitted in Pigweed. Aim for consistency with existing 938code and the C++ Standard Library. Be very careful mixing signed and unsigned 939integers. 940 941Features not in the C++ standard 942================================ 943Avoid features not available in standard C++. This includes compiler extensions 944and features from other standards like POSIX. 945 946For example, use ``ptrdiff_t`` instead of POSIX's ``ssize_t``, unless 947interacting with a POSIX API in intentionally non-portable code. Never use 948POSIX functions with suitable standard or Pigweed alternatives, such as 949``strnlen`` (use ``pw::string::NullTerminatedLength`` instead). 950