Skip to content
C++
Compiler
Updated 2026-05-01T00:00:00.000Z

GCC

GNU Compiler Collection — the workhorse of open-source C++ development. Widest platform and architecture support, mature optimizer, de-facto Linux standard.

TL;DR

GCC is the de-facto C++ compiler on Linux and the only serious choice for many embedded architectures. Use GCC 13+ for full C++23 partial support and GCC 14+ for improved C++23 conformance. Prefer -O2 for release builds and always pair with ASan/UBSan during development.

bash
# Install (Ubuntu/Debian)
sudo apt install gcc-14 g++-14

# Compile
g++-14 -std=c++23 -O2 -Wall -Wextra -o myapp main.cpp

# With sanitizers (dev builds)
g++-14 -std=c++20 -O1 -fsanitize=address,undefined -fno-omit-frame-pointer -o myapp main.cpp

Standards support

StandardStatusFlag
C++11Full-std=c++11
C++14Full-std=c++14
C++17Full-std=c++17
C++20Full (GCC 13+)-std=c++20
C++23Partial (GCC 14+)-std=c++23
C++26In progress-std=c++26

Use --std=c++20 (or c++17) as your minimum in new projects. Avoid c++0x/c++1y — those are legacy spellings.

Essential flags

Warning flags

bash
# Recommended baseline
-Wall -Wextra -Wpedantic

# Stronger — catches more real bugs
-Wall -Wextra -Wpedantic -Wshadow -Wconversion -Wsign-conversion \
  -Wnull-dereference -Wdouble-promotion -Wformat=2

# For header-only libs (treat warnings as errors)
-Werror

Optimization flags

bash
-O0    # No optimization — fast compilation, best for debugging
-O1    # Minimal optimization — good for sanitizer builds
-O2    # Standard release — best balance (use this)
-O3    # Aggressive — more vectorization, sometimes slower due to code size
-Os    # Optimize for size (embedded)
-Og    # Debug-friendly optimization (GCC only)

Debugging

bash
-g        # Include debug info (DWARF)
-g3       # Include macro definitions too
-ggdb     # GDB-specific extensions
-fno-omit-frame-pointer  # Keep frame pointer for profilers/sanitizers
bash
# Enable LTO (major win for release builds)
g++ -O2 -flto -fuse-linker-plugin -o myapp main.cpp lib.cpp

# Thin LTO (parallel, faster than full LTO)
g++ -O2 -flto=auto -o myapp main.cpp lib.cpp

Architecture targets

GCC supports more target architectures than any other compiler:

bash
# Cross-compile for ARM (embedded)
arm-none-eabi-g++ -std=c++20 -mcpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=hard \
  -Os -fno-exceptions -fno-rtti -o firmware.elf main.cpp

# RISC-V
riscv64-unknown-elf-g++ -march=rv64imafd -mabi=lp64d -o app main.cpp

# WebAssembly (via Emscripten, which uses LLVM internally but has GCC-compatible flags)
em++ -std=c++20 -O2 -o app.wasm main.cpp

Sanitizers

bash
# AddressSanitizer (heap/stack buffer overflows, use-after-free)
-fsanitize=address

# UndefinedBehaviorSanitizer (signed overflow, null deref, etc.)
-fsanitize=undefined

# ThreadSanitizer (data races)
-fsanitize=thread

# Combine ASan + UBSan (most useful combination)
-fsanitize=address,undefined -fno-omit-frame-pointer

Note: ASan and TSan are mutually exclusive.

Useful diagnostics flags

bash
# Show include paths resolved
-H

# Show where a macro is defined
-fdump-macro-expansion

# Show compilation time breakdown
-ftime-report

# Preprocessor output only
-E

# Assembly output (readable)
-S -fverbose-asm

CMake integration

cmake
cmake_minimum_required(VERSION 3.20)
project(myapp CXX)

set(CMAKE_CXX_STANDARD 20)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

add_executable(myapp main.cpp)

# Apply warning flags
target_compile_options(myapp PRIVATE
  $<$<CXX_COMPILER_ID:GNU>:-Wall -Wextra -Wpedantic -Wshadow>
)

# Enable LTO for Release builds
set_target_properties(myapp PROPERTIES INTERPROCEDURAL_OPTIMIZATION_RELEASE ON)

GCC vs Clang — when to prefer GCC

SituationPrefer
Linux target, embedded (ARM/RISC-V)GCC
macOS developmentClang
Best error messagesClang
Widest architecture supportGCC
clang-tidy / clang-formatClang
Maximum LTO performance on x86Similar
RISC-V, MIPS, PowerPCGCC

In practice, testing against both GCC and Clang in CI is the best approach — they catch different issues.

Common pitfalls

Implicit function declarations: GCC historically warned about these; in C23 they're errors. Always use proper headers.

Integer overflow: GCC assumes signed integer overflow doesn't happen (UB). Use -fwrapv only if you need wrap-around semantics.

Strict aliasing: GCC optimizes based on strict aliasing rules. Use -fno-strict-aliasing with caution — it disables a real optimization.

-O3 regressions: -O3 enables more aggressive transformations that can hurt performance due to code size increases. Profile before choosing -O3 over -O2.

Edit on GitHubUpdated 2026-05-01T00:00:00.000Z