16d528ed9Sopenharmony_ci# GN Quick Start guide
26d528ed9Sopenharmony_ci
36d528ed9Sopenharmony_ci[TOC]
46d528ed9Sopenharmony_ci
56d528ed9Sopenharmony_ci## Running GN
66d528ed9Sopenharmony_ci
76d528ed9Sopenharmony_ciYou just run `gn` from the command line. For large projects, GN is versioned
86d528ed9Sopenharmony_ciand distributed with the source checkout.
96d528ed9Sopenharmony_ci
106d528ed9Sopenharmony_ci  * For Chromium and Chromium-based projects, there is a script in
116d528ed9Sopenharmony_ci    `depot_tools`, which is presumably in your PATH, with this name. The script
126d528ed9Sopenharmony_ci    will find the binary in the source tree containing the current directory and
136d528ed9Sopenharmony_ci    run it.
146d528ed9Sopenharmony_ci
156d528ed9Sopenharmony_ci  * For Fuchsia in-tree development, run `fx gn ...` which will find the right
166d528ed9Sopenharmony_ci    GN binary and run it with the given arguments.
176d528ed9Sopenharmony_ci
186d528ed9Sopenharmony_ci  * For other projects, see your project's documentation.
196d528ed9Sopenharmony_ci
206d528ed9Sopenharmony_ci## Setting up a build
216d528ed9Sopenharmony_ci
226d528ed9Sopenharmony_ciUnlike some other build systems, with GN you set up your own build directories
236d528ed9Sopenharmony_ciwith the settings you want. This lets you maintain as many different builds in
246d528ed9Sopenharmony_ciparallel as you need.
256d528ed9Sopenharmony_ci
266d528ed9Sopenharmony_ciOnce you set up a build directory, the Ninja files will be automatically
276d528ed9Sopenharmony_ciregenerated if they're out of date when you build in that directory so you
286d528ed9Sopenharmony_cishould not have to re-run GN.
296d528ed9Sopenharmony_ci
306d528ed9Sopenharmony_ciTo make a build directory:
316d528ed9Sopenharmony_ci
326d528ed9Sopenharmony_ci```
336d528ed9Sopenharmony_cign gen out/my_build
346d528ed9Sopenharmony_ci```
356d528ed9Sopenharmony_ci
366d528ed9Sopenharmony_ci## Passing build arguments
376d528ed9Sopenharmony_ci
386d528ed9Sopenharmony_ciSet build arguments on your build directory by running:
396d528ed9Sopenharmony_ci
406d528ed9Sopenharmony_ci```
416d528ed9Sopenharmony_cign args out/my_build
426d528ed9Sopenharmony_ci```
436d528ed9Sopenharmony_ci
446d528ed9Sopenharmony_ciThis will bring up an editor. Type build args into that file like this:
456d528ed9Sopenharmony_ci
466d528ed9Sopenharmony_ci```
476d528ed9Sopenharmony_ciis_component_build = true
486d528ed9Sopenharmony_ciis_debug = false
496d528ed9Sopenharmony_ci```
506d528ed9Sopenharmony_ci
516d528ed9Sopenharmony_ciThe available variables will depend on your build (this example is from
526d528ed9Sopenharmony_ciChromium). You can see the list of available arguments and their default values
536d528ed9Sopenharmony_ciby typing
546d528ed9Sopenharmony_ci
556d528ed9Sopenharmony_ci```
566d528ed9Sopenharmony_cign args --list out/my_build
576d528ed9Sopenharmony_ci```
586d528ed9Sopenharmony_ci
596d528ed9Sopenharmony_cion the command line. Note that you have to specify the build directory
606d528ed9Sopenharmony_cifor this command because the available arguments can change according
616d528ed9Sopenharmony_cito the build.
626d528ed9Sopenharmony_ci
636d528ed9Sopenharmony_ciChrome developers can also read the [Chrome-specific build
646d528ed9Sopenharmony_ciconfiguration](http://www.chromium.org/developers/gn-build-configuration)
656d528ed9Sopenharmony_ciinstructions for more information.
666d528ed9Sopenharmony_ci
676d528ed9Sopenharmony_ci## Cross-compiling to a target OS or architecture
686d528ed9Sopenharmony_ci
696d528ed9Sopenharmony_ciRun `gn args out/Default` (substituting your build directory as needed) and
706d528ed9Sopenharmony_ciadd one or more of the following lines for common cross-compiling options.
716d528ed9Sopenharmony_ci
726d528ed9Sopenharmony_ci```
736d528ed9Sopenharmony_citarget_os = "chromeos"
746d528ed9Sopenharmony_citarget_os = "android"
756d528ed9Sopenharmony_ci
766d528ed9Sopenharmony_citarget_cpu = "arm"
776d528ed9Sopenharmony_citarget_cpu = "x86"
786d528ed9Sopenharmony_citarget_cpu = "x64"
796d528ed9Sopenharmony_ci```
806d528ed9Sopenharmony_ci
816d528ed9Sopenharmony_ciSee [GN cross compiles](cross_compiles.md) for more info.
826d528ed9Sopenharmony_ci
836d528ed9Sopenharmony_ci## Step-by-step
846d528ed9Sopenharmony_ci
856d528ed9Sopenharmony_ci### Adding a build file
866d528ed9Sopenharmony_ci
876d528ed9Sopenharmony_ciGo to the directory `examples/simple_build`. This is the root of a minimal GN
886d528ed9Sopenharmony_cirepository.
896d528ed9Sopenharmony_ci
906d528ed9Sopenharmony_ciIn that directory there is a `tutorial` directory. There is already a
916d528ed9Sopenharmony_ci`tutorial.cc` file that's not hooked up to the build. Create a new `BUILD.gn`
926d528ed9Sopenharmony_cifile in that directory for our new target.
936d528ed9Sopenharmony_ci
946d528ed9Sopenharmony_ci```
956d528ed9Sopenharmony_ciexecutable("tutorial") {
966d528ed9Sopenharmony_ci  sources = [
976d528ed9Sopenharmony_ci    "tutorial.cc",
986d528ed9Sopenharmony_ci  ]
996d528ed9Sopenharmony_ci}
1006d528ed9Sopenharmony_ci```
1016d528ed9Sopenharmony_ci
1026d528ed9Sopenharmony_ciNow we just need to tell the build about this new target. Open the `BUILD.gn`
1036d528ed9Sopenharmony_cifile in the parent (`simple_build`) directory. GN starts by loading this root
1046d528ed9Sopenharmony_cifile, and then loads all dependencies ourward from here, so we just need to add
1056d528ed9Sopenharmony_cia reference to our new target from this file.
1066d528ed9Sopenharmony_ci
1076d528ed9Sopenharmony_ciYou could add our new target as a dependency from one of the existing targets in
1086d528ed9Sopenharmony_cithe `simple_build/BUILD.gn` file, but it usually doesn't make a lot of sense to
1096d528ed9Sopenharmony_cihave an executable as a depdency of another executable (they can't be linked).
1106d528ed9Sopenharmony_ciSo let's make a "tools" group. In GN, a "group" is just a collection of
1116d528ed9Sopenharmony_cidependencies that's not complied or linked:
1126d528ed9Sopenharmony_ci
1136d528ed9Sopenharmony_ci```
1146d528ed9Sopenharmony_cigroup("tools") {
1156d528ed9Sopenharmony_ci  deps = [
1166d528ed9Sopenharmony_ci    # This will expand to the name "//tutorial:tutorial" which is the full name
1176d528ed9Sopenharmony_ci    # of our new target. Run "gn help labels" for more.
1186d528ed9Sopenharmony_ci    "//tutorial",
1196d528ed9Sopenharmony_ci  ]
1206d528ed9Sopenharmony_ci}
1216d528ed9Sopenharmony_ci```
1226d528ed9Sopenharmony_ci
1236d528ed9Sopenharmony_ci### Testing your addition
1246d528ed9Sopenharmony_ci
1256d528ed9Sopenharmony_ciFrom the command line in the `simple_build` directory:
1266d528ed9Sopenharmony_ci
1276d528ed9Sopenharmony_ci```
1286d528ed9Sopenharmony_cign gen out
1296d528ed9Sopenharmony_cininja -C out tutorial
1306d528ed9Sopenharmony_ciout/tutorial
1316d528ed9Sopenharmony_ci```
1326d528ed9Sopenharmony_ci
1336d528ed9Sopenharmony_ciYou should see "Hello, world." output to the console.
1346d528ed9Sopenharmony_ci
1356d528ed9Sopenharmony_ciSide note: GN encourages target names for static libraries that aren't globally
1366d528ed9Sopenharmony_ciunique. To build one of these, you can pass the label with its path (but no leading
1376d528ed9Sopenharmony_ci"//") to ninja:
1386d528ed9Sopenharmony_ci
1396d528ed9Sopenharmony_ci```
1406d528ed9Sopenharmony_cininja -C out some/path/to/target:my_target
1416d528ed9Sopenharmony_ci```
1426d528ed9Sopenharmony_ci
1436d528ed9Sopenharmony_ci### Declaring dependencies
1446d528ed9Sopenharmony_ci
1456d528ed9Sopenharmony_ciLet's look at the targets defined in
1466d528ed9Sopenharmony_ci[examples/simple_build/BUILD.gn](../examples/simple_build/BUILD.gn). There is a
1476d528ed9Sopenharmony_cistatic library that defines one function, `GetStaticText()`:
1486d528ed9Sopenharmony_ci
1496d528ed9Sopenharmony_ci```
1506d528ed9Sopenharmony_cistatic_library("hello_static") {
1516d528ed9Sopenharmony_ci  sources = [
1526d528ed9Sopenharmony_ci    "hello_static.cc",
1536d528ed9Sopenharmony_ci    "hello_static.h",
1546d528ed9Sopenharmony_ci  ]
1556d528ed9Sopenharmony_ci}
1566d528ed9Sopenharmony_ci```
1576d528ed9Sopenharmony_ci
1586d528ed9Sopenharmony_ciThere is also a shared library that defines one function `GetSharedText()`:
1596d528ed9Sopenharmony_ci
1606d528ed9Sopenharmony_ci```
1616d528ed9Sopenharmony_cishared_library("hello_shared") {
1626d528ed9Sopenharmony_ci  sources = [
1636d528ed9Sopenharmony_ci    "hello_shared.cc",
1646d528ed9Sopenharmony_ci    "hello_shared.h",
1656d528ed9Sopenharmony_ci  ]
1666d528ed9Sopenharmony_ci
1676d528ed9Sopenharmony_ci  defines = [ "HELLO_SHARED_IMPLEMENTATION" ]
1686d528ed9Sopenharmony_ci}
1696d528ed9Sopenharmony_ci```
1706d528ed9Sopenharmony_ci
1716d528ed9Sopenharmony_ciThis also illustrates how to set preprocessor defines for a target. To set more
1726d528ed9Sopenharmony_cithan one or to assign values, use this form:
1736d528ed9Sopenharmony_ci
1746d528ed9Sopenharmony_ci```
1756d528ed9Sopenharmony_cidefines = [
1766d528ed9Sopenharmony_ci  "HELLO_SHARED_IMPLEMENTATION",
1776d528ed9Sopenharmony_ci  "ENABLE_DOOM_MELON=0",
1786d528ed9Sopenharmony_ci]
1796d528ed9Sopenharmony_ci```
1806d528ed9Sopenharmony_ci
1816d528ed9Sopenharmony_ciNow let's look at the executable that depends on these two libraries:
1826d528ed9Sopenharmony_ci
1836d528ed9Sopenharmony_ci```
1846d528ed9Sopenharmony_ciexecutable("hello") {
1856d528ed9Sopenharmony_ci  sources = [
1866d528ed9Sopenharmony_ci    "hello.cc",
1876d528ed9Sopenharmony_ci  ]
1886d528ed9Sopenharmony_ci
1896d528ed9Sopenharmony_ci  deps = [
1906d528ed9Sopenharmony_ci    ":hello_shared",
1916d528ed9Sopenharmony_ci    ":hello_static",
1926d528ed9Sopenharmony_ci  ]
1936d528ed9Sopenharmony_ci}
1946d528ed9Sopenharmony_ci```
1956d528ed9Sopenharmony_ci
1966d528ed9Sopenharmony_ciThis executable includes one source file and depends on the previous
1976d528ed9Sopenharmony_citwo libraries. Labels starting with a colon refer to a target with that name in
1986d528ed9Sopenharmony_cithe current BUILD.gn file.
1996d528ed9Sopenharmony_ci
2006d528ed9Sopenharmony_ci### Test the binary
2016d528ed9Sopenharmony_ci
2026d528ed9Sopenharmony_ciFrom the command line in the `simple_build` directory:
2036d528ed9Sopenharmony_ci
2046d528ed9Sopenharmony_ci```
2056d528ed9Sopenharmony_cininja -C out hello
2066d528ed9Sopenharmony_ciout/hello
2076d528ed9Sopenharmony_ci```
2086d528ed9Sopenharmony_ci
2096d528ed9Sopenharmony_ciNote that you **didn't** need to re-run GN. GN will automatically rebuild
2106d528ed9Sopenharmony_cithe ninja files when any build file has changed. You know this happens
2116d528ed9Sopenharmony_ciwhen ninja prints `[1/1] Regenerating ninja files` at the beginning of
2126d528ed9Sopenharmony_ciexecution.
2136d528ed9Sopenharmony_ci
2146d528ed9Sopenharmony_ci### Putting settings in a config
2156d528ed9Sopenharmony_ci
2166d528ed9Sopenharmony_ciUsers of a library often need compiler flags, defines, and include directories
2176d528ed9Sopenharmony_ciapplied to them. To do this, put all such settings into a "config" which is a
2186d528ed9Sopenharmony_cinamed collection of settings (but not sources or dependencies):
2196d528ed9Sopenharmony_ci
2206d528ed9Sopenharmony_ci```
2216d528ed9Sopenharmony_ciconfig("my_lib_config") {
2226d528ed9Sopenharmony_ci  defines = [ "ENABLE_DOOM_MELON" ]
2236d528ed9Sopenharmony_ci  include_dirs = [ "//third_party/something" ]
2246d528ed9Sopenharmony_ci}
2256d528ed9Sopenharmony_ci```
2266d528ed9Sopenharmony_ci
2276d528ed9Sopenharmony_ciTo apply a config's settings to a target, add it to the `configs` list:
2286d528ed9Sopenharmony_ci
2296d528ed9Sopenharmony_ci```
2306d528ed9Sopenharmony_cistatic_library("hello_shared") {
2316d528ed9Sopenharmony_ci  ...
2326d528ed9Sopenharmony_ci  # Note "+=" here is usually required, see "default configs" below.
2336d528ed9Sopenharmony_ci  configs += [
2346d528ed9Sopenharmony_ci    ":my_lib_config",
2356d528ed9Sopenharmony_ci  ]
2366d528ed9Sopenharmony_ci}
2376d528ed9Sopenharmony_ci```
2386d528ed9Sopenharmony_ci
2396d528ed9Sopenharmony_ciA config can be applied to all targets that depend on the current one by putting
2406d528ed9Sopenharmony_ciits label in the `public_configs` list:
2416d528ed9Sopenharmony_ci
2426d528ed9Sopenharmony_ci```
2436d528ed9Sopenharmony_cistatic_library("hello_shared") {
2446d528ed9Sopenharmony_ci  ...
2456d528ed9Sopenharmony_ci  public_configs = [
2466d528ed9Sopenharmony_ci    ":my_lib_config",
2476d528ed9Sopenharmony_ci  ]
2486d528ed9Sopenharmony_ci}
2496d528ed9Sopenharmony_ci```
2506d528ed9Sopenharmony_ci
2516d528ed9Sopenharmony_ciThe `public_configs` also applies to the current target, so there's no need to
2526d528ed9Sopenharmony_cilist a config in both places.
2536d528ed9Sopenharmony_ci
2546d528ed9Sopenharmony_ci### Default configs
2556d528ed9Sopenharmony_ci
2566d528ed9Sopenharmony_ciThe build configuration will set up some settings that apply to every target by
2576d528ed9Sopenharmony_cidefault. These will normally be set as a default list of configs. You can see
2586d528ed9Sopenharmony_cithis using the "print" command which is useful for debugging:
2596d528ed9Sopenharmony_ci
2606d528ed9Sopenharmony_ci```
2616d528ed9Sopenharmony_ciexecutable("hello") {
2626d528ed9Sopenharmony_ci  print(configs)
2636d528ed9Sopenharmony_ci}
2646d528ed9Sopenharmony_ci```
2656d528ed9Sopenharmony_ci
2666d528ed9Sopenharmony_ciRunning GN will print something like:
2676d528ed9Sopenharmony_ci
2686d528ed9Sopenharmony_ci```
2696d528ed9Sopenharmony_ci$ gn gen out
2706d528ed9Sopenharmony_ci["//build:compiler_defaults", "//build:executable_ldconfig"]
2716d528ed9Sopenharmony_ciDone. Made 5 targets from 5 files in 9ms
2726d528ed9Sopenharmony_ci```
2736d528ed9Sopenharmony_ci
2746d528ed9Sopenharmony_ciTargets can modify this list to change their defaults. For example, the build
2756d528ed9Sopenharmony_cisetup might turn off exceptions by default by adding a `no_exceptions` config,
2766d528ed9Sopenharmony_cibut a target might re-enable them by replacing it with a different one:
2776d528ed9Sopenharmony_ci
2786d528ed9Sopenharmony_ci```
2796d528ed9Sopenharmony_ciexecutable("hello") {
2806d528ed9Sopenharmony_ci  ...
2816d528ed9Sopenharmony_ci  configs -= [ "//build:no_exceptions" ]  # Remove global default.
2826d528ed9Sopenharmony_ci  configs += [ "//build:exceptions" ]  # Replace with a different one.
2836d528ed9Sopenharmony_ci}
2846d528ed9Sopenharmony_ci```
2856d528ed9Sopenharmony_ci
2866d528ed9Sopenharmony_ciOur print command from above could also be expressed using string interpolation.
2876d528ed9Sopenharmony_ciThis is a way to convert values to strings. It uses the symbol "$" to refer to a
2886d528ed9Sopenharmony_civariable:
2896d528ed9Sopenharmony_ci
2906d528ed9Sopenharmony_ci```
2916d528ed9Sopenharmony_ciprint("The configs for the target $target_name are $configs")
2926d528ed9Sopenharmony_ci```
2936d528ed9Sopenharmony_ci
2946d528ed9Sopenharmony_ci## Add a new build argument
2956d528ed9Sopenharmony_ci
2966d528ed9Sopenharmony_ciYou declare which arguments you accept and specify default values via
2976d528ed9Sopenharmony_ci`declare_args`.
2986d528ed9Sopenharmony_ci
2996d528ed9Sopenharmony_ci```
3006d528ed9Sopenharmony_cideclare_args() {
3016d528ed9Sopenharmony_ci  enable_teleporter = true
3026d528ed9Sopenharmony_ci  enable_doom_melon = false
3036d528ed9Sopenharmony_ci}
3046d528ed9Sopenharmony_ci```
3056d528ed9Sopenharmony_ci
3066d528ed9Sopenharmony_ciSee `gn help buildargs` for an overview of how this works.
3076d528ed9Sopenharmony_ciSee `gn help declare_args` for specifics on declaring them.
3086d528ed9Sopenharmony_ci
3096d528ed9Sopenharmony_ciIt is an error to declare a given argument more than once in a given scope, so
3106d528ed9Sopenharmony_cicare should be used in scoping and naming arguments.
3116d528ed9Sopenharmony_ci
3126d528ed9Sopenharmony_ci## Don't know what's going on?
3136d528ed9Sopenharmony_ci
3146d528ed9Sopenharmony_ciYou can run GN in verbose mode to see lots of messages about what it's
3156d528ed9Sopenharmony_cidoing. Use `-v` for this.
3166d528ed9Sopenharmony_ci
3176d528ed9Sopenharmony_ci### The "desc" command
3186d528ed9Sopenharmony_ci
3196d528ed9Sopenharmony_ciYou can run `gn desc <build_dir> <targetname>` to get information about
3206d528ed9Sopenharmony_cia given target:
3216d528ed9Sopenharmony_ci
3226d528ed9Sopenharmony_ci```
3236d528ed9Sopenharmony_cign desc out/Default //foo/bar:say_hello
3246d528ed9Sopenharmony_ci```
3256d528ed9Sopenharmony_ci
3266d528ed9Sopenharmony_ciwill print out lots of exciting information. You can also print just one
3276d528ed9Sopenharmony_cisection. Lets say you wanted to know where your `TWO_PEOPLE` define
3286d528ed9Sopenharmony_cicame from on the `say_hello` target:
3296d528ed9Sopenharmony_ci
3306d528ed9Sopenharmony_ci```
3316d528ed9Sopenharmony_ci> gn desc out/Default //foo/bar:say_hello defines --blame
3326d528ed9Sopenharmony_ci...lots of other stuff omitted...
3336d528ed9Sopenharmony_ci  From //foo/bar:hello_config
3346d528ed9Sopenharmony_ci       (Added by //foo/bar/BUILD.gn:12)
3356d528ed9Sopenharmony_ci    TWO_PEOPLE
3366d528ed9Sopenharmony_ci```
3376d528ed9Sopenharmony_ci
3386d528ed9Sopenharmony_ciAnother particularly interesting variation:
3396d528ed9Sopenharmony_ci
3406d528ed9Sopenharmony_ci```
3416d528ed9Sopenharmony_cign desc out/Default //base:base_i18n deps --tree
3426d528ed9Sopenharmony_ci```
3436d528ed9Sopenharmony_ci
3446d528ed9Sopenharmony_ciSee `gn help desc` for more.
345