gn的帮助说明

gn的帮助说明

# 使用步骤

1. 创建.gn
1. 指定根目录
2. 用 buildconfig 來指定构建配置的位置
2. 创建build/BUILDCONFIG.gn
1. 指定要使用的 toolchain
2. 设定编译参数
3. 建立 build/toolchains/BUILD.gn
1. 指定工具链中各工具的使用命令(规则)
4. 建立 BUILD.gn
1. 在 root/ 新增一个 BUILD.gn
2. 指定最终的目标由哪些sources编译链接成
5. 构建
1. gn gen out
1. 在out中生成ninja构建脚本
2. ninja -C out
1. 用 ninja 执行构建脚本
3. 重新构建时，不需要再生成新的构建脚本

# 快速入门

## 配置一个构建

gn gen out/test


## 传递构建参数

gn args out/test


gn args --list out/test


## 整体构建流程

• 在当前目录中查找.gn 文件，然后沿着目录树向上走，直到找到.gn文件所在目录为止。
• 将此目录设置为“source root”并解析此文件以查找构建配置文件的名称。
• 执行构建配置文件（这是默认的工具链）。
• 将BUILD.gn文件加载到根目录中。
• 递归加载其他目录BUILD.gn以解析所有当前依赖项。
• 如果在指定位置找不到BUILD文件，GN将查看tools/gn/secondary中的相应位置。
• 解决目标的依赖关系后，将.ninja文件写入磁盘。
• 解决所有目标后，写出根build.ninja文件。

## Ninja 构建系统

1. 在Web浏览器中浏览依赖关系图

 ninja -t browse --port=8000 --no-browser mytarget

2. 以自动图形布局工具graphviz的语法输出一个文件

 ninja -t graph mytarget | dot -Tpng -ograph.png


## 目标

• action：运行一个脚本来生成一个文件。
• action_foreach：为每个源文件运行一次脚本。
• bundle_data：声明数据加入到Mac / iOS包。
• create_bundle：创建一个Mac / iOS包。
• executable：生成一个可执行文件。
• group：引用一个或多个其他目标的虚拟依赖关系节点。
• shared_library：.dll或.so。
• source_set：一个轻量级的虚拟静态库（通常比真正的静态库更可取，因为它的构建速度会更快）。
• static_library：.lib或.a文件（通常你会想要一个source_set）。

• component：源集或共享库，取决于构建类型。
• test：测试可执行文件 在移动设备上，这将为测试创建适当的本机应用程序类型。
• app：可执行文件或Mac/iOS应用程序。
• android_apk：制作一个APK。有很多其他的Android模版，看//build/config/android/rules.gni。

## CONFIGS

config("myconfig") {
includes = [ "src/include" ]
defines = [ "ENABLE_DOOM_MELON" ]
}


executable("doom_melon") {
configs = [ ":myconfig" ]
}


## sources

sources: Source files for a target

sources: 目标的源文件

A list of files. Non-absolute paths will be resolved relative to the current build file.

Sources for binary targets

For binary targets (source sets, executables, and libraries), the known file types will be compiled with the associated tools. Unknown file types and headers will be skipped. However, you should still list all C/C+ header files so GN knows about the existence of those files for the purposes of include checking.

As a special case, a file ending in “.def” will be treated as a Windows module definition file. It will be appended to the link line with a preceding “/DEF:” string. There must be at most one .def file in a target and they do not cross dependency boundaries (so specifying a .def file in a static library or source set will have no effect on the executable or shared library they’re linked into).

For Rust targets that do not specify a crate_root, then the crate_root will look for a lib.rs file (or main.rs for executable) or a single file in sources, if sources contains only one file.

Sources for non-binary targets

action_foreach

The sources are the set of files that the script will be executed over. The script will run once per file.

resources 是脚本将在其上执行的文件集。该脚本将对每个文件运行一次。


action

The sources will be treated the same as inputs. See "gn help inputs" for more information and usage advice.

sources 将被视为与输入相同。有关更多信息和使用建议，请参阅“gn help inputs”。


copy

The source are the source files to copy.

sources 是要复制的源文件


## source_set

source_set:声明一个源码集目标

source_set目标的语言由其源码中的扩展名决定

### C-语言 source_sets

A source set is a collection of sources that get compiled, but are not linked to produce any kind of library. Instead, the resulting object files are implicitly added to the linker line of all targets that depend on the source set.

source_sets是要编译的文件集合，这些.o文件被导出给链接器的搜索空间

In most cases, a source set will behave like a static library, except no actual library file will be produced. This will make the build go a little faster by skipping creation of a large static library, while maintaining the organizational benefits of focused build targets.

The main difference between a source set and a static library is around handling of exported symbols. Most linkers assume declaring a function exported means exported from the static library. The linker can then do dead code elimination to delete code not reachable from exported functions.

A source set will not do this code elimination since there is no link step. This allows you to link many source sets into a shared library and have the “exported symbol” notation indicate “export from the final shared library and not from the intermediate targets.” There is no way to express this concept when linking multiple static libraries into a shared library.

### Rust-语言 source_sets

A Rust source set is a collection of sources that get passed along to the final target that depends on it. No compilation is performed, and the source files are simply added as dependencies on the eventual rustc invocation that would produce a binary.

Rust源码集是传递到依赖于它的最终目标的源的集合。不执行编译，源文件只是作为将生成二进制文件的最终rustc调用的依赖项添加。

### 变量

Flags: cflags, cflags_c, cflags_cc, cflags_objc, cflags_objcc, asmflags, defines, include_dirs, inputs, ldflags, lib_dirs, libs, precompiled_header, precompiled_source, rustflags, rustenv Deps: data_deps, deps, public_deps Dependent configs: all_dependent_configs, public_configs General: check_includes, configs, data, friend, inputs, metadata, output_name, output_extension, public, sources, testonly, visibility

## defines

defines: C preprocessor defines.

A list of strings

These strings will be passed to the C/C++ compiler as #defines. The strings may or may not include an “=” to assign a value.

Ordering of flags and values

1. Those set on the current target (not in a config).
2. Those set on the “configs” on the target in order that the configs appear in the list.
3. Those set on the “all_dependent_configs” on the target in order that the configs appear in the list.
4. Those set on the “public_configs” on the target in order that those configs appear in the list.
5. all_dependent_configs pulled from dependencies, in the order of the “deps” list. This is done recursively. If a config appears more than once, only the first occurence will be used.
6. public_configs pulled from dependencies, in the order of the “deps” list. If a dependency is public, they will be applied recursively.

1. 那些在当前目标上设置的(不是在配置中)。
2. 那些设置在“配置”上的目标，以使配置出现在列表中。
3. 那些在目标上的“all_dependent_configs”上设置的，以便配置出现在列表中。
4. 那些在目标上的“public_configs”上设置的，以便那些配置出现在列表中。
5. 从依赖项中提取的All_dependent_configs，按照“deps”列表的顺序。这是递归地完成的。如果一个配置出现多次，则只使用第一次出现的配置。
6. 从依赖项中提取的Public_configs，按照“deps”列表的顺序。如果依赖项是公共的，则将递归地应用它们。


Example

defines = [ “AWESOME_FEATURE”, “LOG_LEVEL=3” ]

## include_dirs

• include_dirs:其他包含目录

• 源码目录的列表
• The directories in this list will be added to the include path for the files in the affected target.
• 这个列表中的目录将被添加到受影响目标涉及的各文件的include路径中

### 标志和值的排序

1. 那些在当前目标上设置的(不是在配置config中)。
2. 那些设置在“配置config”上的目标，以使配置出现在列表中
3. 那些在目标上的“all_dependent_configs”上设置的，以便配置出现在列表中。
4. 那些在目标上的“public_configs”上设置的，以便那些配置出现在列表中。
5. 从依赖项中提取的All_dependent_configs，按照“deps”列表的顺序。这是递归地完成的。如果一个配置出现多次，则只使用第一次出现的配置。
6. 从依赖项中提取的Public_configs，按照“deps”列表的顺序。如果依赖项是公共的，则将递归地应用它们。

### Example

include_dirs = [ “src/include”, “//third_party/foo” ]

## declare_args()

declare_args: Declare build arguments.

declare_args:声明构建参数

Introduces the given arguments into the current scope. If they are not specified on the command line or in a toolchain’s arguments, the default values given in the declare_args block will be used. However, these defaults will not override command-line values.

The precise behavior of declare args is:

declare args的精确行为是:

1. The declare_args() block executes. Any variable defined in the enclosing scope is available for reading, but any variable defined earlier in the current scope is not (since the overrides haven’t been applied yet).

执行declare_args()块。在封闭作用域中定义的任何变量都可以读取，但在当前作用域中较早定义的任何变量都不能读取(因为还没有应用覆盖)。

2. At the end of executing the block, any variables set within that scope are saved, with the values specified in the block used as the “default value” for that argument. Once saved, these variables are available for override via args.gn.

在执行块结束时，将保存在该范围内设置的所有变量，并将块中指定的值用作该参数的“默认值”。保存后，这些变量可通过args.gn进行重写

3. User-defined overrides are applied. Anything set in “gn args” now overrides any default values. The resulting set of variables is promoted to be readable from the following code in the file.

应用用户定义的覆盖。“gn args”中设置的任何内容现在都会覆盖任何默认值。生成的变量集将升级为可从文件的后续代码读取

This has some ramifications that may not be obvious:

- You should not perform difficult work inside a declare_args block since this only sets a default value that may be discarded. In particular, don't use the result of exec_script() to set the default value. If you want to have a script-defined default, set some default "undefined" value like [], "", or -1, and after the declare_args block, call exec_script if the value is unset by the user.

你不应该在declare_args块中执行困难的工作，因为这只设置了一个可能被丢弃的默认值。特别是，不要使用exec_script()的结果来设置默认值。如果要让脚本定义默认值，请设置一些默认的“未定义”值，如[]、""或-1，如果用户未设置该值，请在declare_args块之后调用exec_script

- Because you cannot read the value of a variable defined in the same block, if you need to make the default value of one arg depend on the possibly-overridden value of another, write two separate declare_args() blocks:

由于无法读取同一块中定义的变量的值，如果需要使一个参数的默认值取决于另一个参数的可能重写值，请编写两个单独的declare_args()块

java
declare_args() {
enable_foo = true
}
declare_args() {
# Bar defaults to same user-overridden state as foo.
enable_bar = enable_foo
}



Example

java
declare_args() {
enable_teleporter = true
enable_doom_melon = false
}



  gn --args="enable_doom_melon=true enable_teleporter=true"


## buildargs

Build Arguments Overview

Build arguments are variables passed in from outside of the build that build files can query to determine how the build works.

How build arguments are set

First, system default arguments are set based on the current system. The built-in arguments are:

• host_cpu
• host_os
• current_cpu
• current_os
• target_cpu
• target_os

Next, project-specific overrides are applied. These are specified inside the default_args variable of //.gn. See “gn help dotfile” for more.

If specified, arguments from the –args command line flag are used. If that flag is not specified, args from previous builds in the build directory will be used (this is in the file args.gn in the build directory).

Last, for targets being compiled with a non-default toolchain, the toolchain overrides are applied. These are specified in the toolchain_args section of a toolchain definition. The use-case for this is that a toolchain may be building code for a different platform, and that it may want to always specify Posix, for example. See “gn help toolchain” for more.

If you specify an override for a build argument that never appears in a “declare_args” call, a nonfatal error will be displayed.

Examples

- gn args out/FooBar

Create the directory out/FooBar and open an editor. You would type something like this into that file:

在/FooBar中创建目录并打开编辑器。你可以在文件中输入如下内容:

bash
enable_doom_melon=false
os="android"


- gn gen out/FooBar --args="enable_doom_melon=true os=\"android\""

This will overwrite the build directory with the given arguments. (Note that the quotes inside the args command will usually need to be escaped for your shell to pass through strings values.)

这将使用给定的参数覆写构建目录。(请注意，args命令中的引号通常需要转义，以便shell传递字符串值。)


How build arguments are used

If you want to use an argument, you use declare_args() and specify default values. These default values will apply if none of the steps listed in the “How build arguments are set” section above apply to the given argument, but the defaults will not override any of these.

Often, the root build config file will declare global arguments that will be passed to all buildfiles. Individual build files can also specify arguments that apply only to those files. It is also useful to specify build args in an “import”-ed file if you want such arguments to apply to multiple buildfiles.

## template

template: Define a template rule.

template:定义模板规则。

A template defines a custom name that acts like a function. It provides a way to add to the built-in target types.

The template() function is used to declare a template. To invoke the template, just use the name of the template like any other target type.

template()函数用于声明一个模板。要调用模板，只需像使用任何其他目标类型一样使用模板的名称。

Often you will want to declare your template in a special file that other files will import (see “gn help import”) so your template rule can be shared across build files.

Variables and templates:

When you call template() it creates a closure around all variables currently in scope with the code in the template block. When the template is invoked, the closure will be executed.

When the template is invoked, the code in the caller is executed and passed to the template code as an implicit “invoker” variable. The template uses this to read state out of the invoking code.

One thing explicitly excluded from the closure is the “current directory” against which relative file names are resolved. The current directory will be that of the invoking code, since typically that code specifies the file names. This means all files internal to the template should use absolute names.

A template will typically forward some or all variables from the invoking scope to a target that it defines. Often, such variables might be optional. Use the pattern:

java
if (defined(invoker.deps)) {
deps = invoker.deps
}



The function forward_variables_from() provides a shortcut to forward one or more or possibly all variables in this manner:

java
# 从invoker转发到deps, public_deps
forward_variables_from(invoker, ["deps", "public_deps"])



Target naming

Your template should almost always define a built-in target with the name the template invoker specified. For example, if you have an IDL template and somebody does:

java
idl("foo") {...



you will normally want this to expand to something defining a source_set or static_library named “foo” (among other things you may need). This way, when another target specifies a dependency on “foo”, the static_library or source_set will be linked.

It is also important that any other targets your template expands to have unique names, or you will get collisions.

Access the invoking name in your template via the implicit “target_name” variable. This should also be the basis for how other targets that a template expands to ensure uniqueness.

A typical example would be a template that defines an action to generate some source files, and a source_set to compile that source. Your template would name the source_set “target_name” because that’s what you want external targets to depend on to link your code. And you would name the action something like “${target_name}_action” to make it unique. The source set would have a dependency on the action to make it run. 一个典型的例子是一个模板，该模板定义了一个生成源文件的操作，以及一个编译该源文件的source_set。您的模板应该将source_set命名为“target_name”，因为您希望外部目标依赖于它来链接您的代码。您可以将操作命名为“${target_name}_action”，以使其惟一。源码集将依赖于使其运行的操作。

Overriding builtin targets

You can use template to redefine a built-in target in which case your template takes a precedence over the built-in one. All uses of the target from within the template definition will refer to the built-in target which makes it possible to extend the behavior of the built-in target:

java
template("shared_library") {
shared_library(shlib) {
forward_variables_from(invoker, "*")
...
}
}



Example of defining a template

python
template("my_idl") {
# Be nice and help callers debug problems by checking that the variables the template requires are defined. This gives a nice message rather than giving the user an error about an undefined variable in the file defining the template
# 友好一点，通过检查模板所需的变量是否已定义，帮助调用者调试问题。
# 这提供了一条很好的消息，而不是给用户一个关于定义模板的文件中未定义变量的错误
#
# You can also use defined() to give default values to variables unspecified by the invoker.
# 还可以使用defined()为调用程序未指定的变量提供默认值。
assert(defined(invoker.sources),
"Need sources in $target_name listing the idl files.") # Name of the intermediate target that does the code gen. This must incorporate the target name so it's unique across template instantiations. # 生成代码的中间目标的名称。这必须包含目标名称，以便它在模板实例化中唯一。 code_gen_target_name = target_name + "_code_gen" # Intermediate target to convert IDL to C source. Note that the name is based on the name the invoker of the template specified. This way, each time the template is invoked we get a unique intermediate action name (since all target names are in the global scope). # 将IDL转换为C源的中间目标。请注意，该名称基于指定模板的调用程序的名称 # 这样，每次调用模板时，我们都会得到一个唯一的中间操作名称（因为所有目标名称都在作用域中） action_foreach(code_gen_target_name) { # Access the scope defined by the invoker via the implicit "invoker" variable. # 通过隐式“invoker”变量访问调用程序定义的范围。 sources = invoker.sources # Note that we need an absolute path for our script file name. The current directory when executing this code will be that of the invoker (this is why we can use the "sources" directly above without having to rebase all of the paths). But if we need to reference a script relative to the template file, we'll need to use an absolute path instead. # 请注意，我们需要脚本文件名的绝对路径。执行此代码时的当前目录将是调用程序的目录（这就是为什么我们可以直接使用上面的“源”，而不必重新设置所有路径的基础）。但是，如果需要引用相对于模板文件的脚本，则需要使用绝对路径。 script = "//tools/idl/idl_code_generator.py" # Tell GN how to expand output names given the sources.See "gn help source_expansion" for more. # 告诉GN如何在给定源的情况下展开输出名称。 # 有关更多信息，请参阅“gn help source_expansion”。 outputs = [ "$target_gen_dir/.cc",
"$target_gen_dir/.h" ] } # Name the source set the same as the template invocation so instancing this template produces something that other targets can link to in their deps. # 将源码集设置命名为与模板调用相同的名称， # 这样实例化该模板将生成其他目标可以在其dep中链接到的内容。 source_set(target_name) { # Generates the list of sources, we get these from the action_foreach above. # 生成源列表，我们从上面的action_foreach获取这些 sources = get_target_outputs(":$code_gen_target_name")

# This target depends on the files produced by the above code gen target.
# 这个目标依赖于上面代码生成的文件
"$target_gen_dir/.cc" ] # Note that since "args" is opaque to GN, if you specify paths here, you will need to convert it to be relative to the build directory using rebase_path(). # 注意，由于“args”对GN不透明，如果您在这里指定路径，您将需要使用rebase_path()将其转换为相对于构建目录。 args = [ "", "-o", rebase_path(relative_target_gen_dir, root_build_dir) + "/.h" ] }   ## toolchain toolchain: Defines a toolchain. A toolchain is a set of commands and build flags used to compile the source code. The toolchain() function defines these commands. toolchain:定义工具链 工具链是用于编译源代码的一组命令和构建标志。toolchain()函数定义了这些命令。  Toolchain overview You can have more than one toolchain in use at once in a build and a target can exist simultaneously in multiple toolchains. A build file is executed once for each toolchain it is referenced in so the GN code can vary all parameters of each target (or which targets exist) on a per-toolchain basis. 您可以在一个构建中同时使用多个工具链，并且一个目标可以同时存在于多个工具链中。构建文件对其所引用的每个工具链执行一次，因此GN代码可以在每个工具链的基础上改变每个目标（或存在哪些目标）的所有参数。 When you have a simple build with only one toolchain, the build config file is loaded only once at the beginning of the build. It must call set_default_toolchain() (see “gn help set_default_toolchain”) to tell GN the label of the toolchain definition to use. The “toolchain_args” section of the toolchain definition is ignored. 当你有一个只有一个工具链的简单构建时，构建配置文件只在构建开始时加载一次。它必须调用set_default_toolchain()（见 “gn help set_default_toolchain”）来告诉GN要使用的工具链定义的标签。工具链定义中的 “toolchain_args “部分被忽略。 When a target has a dependency on a target using different toolchain (see “gn help labels” for how to specify this), GN will start a build using that secondary toolchain to resolve the target. GN will load the build config file with the build arguments overridden as specified in the toolchain_args. Because the default toolchain is already known, calls to set_default_toolchain() are ignored. 当一个目标与使用不同工具链的目标有依赖关系时（参见 “gn help labels”了解如何指定），GN 将使用该第二工具链启动构建，以解析该目标。GN 将加载 build 配置文件，并覆盖 toolchain_args 中指定的 build 参数。 因为默认的工具链已经知道了，对set_default_toolchain()的调用被忽略了。 To load a file in an alternate toolchain, GN does the following: 1. Loads the file with the toolchain definition in it (as determined by the toolchain label). 2. Re-runs the master build configuration file, applying the arguments specified by the toolchain_args section of the toolchain definition. 3. Loads the destination build file in the context of the configuration file in the previous step.  要在备用工具链中加载一个文件，GN会执行以下操作: 1. 加载包含工具链定义的文件(由工具链标签决定)。 2. 重新运行主构建配置文件，应用工具链定义的toolchain_args部分指定的参数。 3.在上一步中，在配置文件的上下文中加载目标构建文件。  The toolchain configuration is two-way. In the default toolchain (i.e. the main build target) the configuration flows from the build config file to the toolchain. The build config file looks at the state of the build (OS type, CPU architecture, etc.) and decides which toolchain to use (via set_default_toolchain()). In secondary toolchains, the configuration flows from the toolchain to the build config file: the “toolchain_args” in the toolchain definition specifies the arguments to re-invoke the build. 工具链的配置是双向的。在默认的工具链中(例如，主要构建目标)，配置从构建配置文件流到工具链。构建配置文件查看构建的状态(OS类型、CPU架构等)，并决定使用哪个工具链(通过set_default_toolchain())。在辅助工具链中，配置从工具链流向构建配置文件:工具链定义中的“toolchain_args”指定了重新调用构建的参数。 Functions and variables tool() The tool() function call specifies the commands to run for a given step. See "gn help tool". tool()函数的调用指定了在给定步骤中要运行的命令。参见 "gn help tool"。  toolchain_args [scope] Overrides for build arguments to pass to the toolchain when invoking it. This is a variable of type "scope" where the variable names correspond to variables in declare_args() blocks. 构建参数的重写，以便在调用工具链时传递给它。 这是一个 "范围" 类型的变量，其中的变量名称对应于 declare_args() 块中的变量。 When you specify a target using an alternate toolchain, the master build configuration file is re-interpreted in the context of that toolchain. toolchain_args allows you to control the arguments passed into this alternate invocation of the build. 当你使用另一个工具链指定一个目标时，主构建配置文件会在该工具链的上下文中被重新解释。toolchain_args允许你控制传递到这个另一个构建调用的参数。 Any default system arguments or arguments passed in via "gn args" will also be passed to the alternate invocation unless explicitly overridden by toolchain_args. 任何默认的系统参数或者通过 "gn args "传递的参数也将被传递给备用调用，除非被toolchain_args明确覆盖。 The toolchain_args will be ignored when the toolchain being defined is the default. In this case, it's expected you want the default argument values. 当被定义的工具链是默认的时候，toolchain_args将被忽略。在这种情况下，预计你想要默认的参数值。 See also "gn help buildargs" for an overview of these arguments. 参见 "gn help buildargs "以了解这些参数的概况。  propagates_configs [boolean, default=false] 传播配置 Determines whether public_configs and all_dependent_configs in this toolchain propagate to targets in other toolchains. 确定此工具链中的public_configs和all_dependent_configs是否传播到其他工具链中的目标 When false (the default), this toolchain will not propagate any configs to targets in other toolchains that depend on it targets inside this toolchain. This matches the most common usage of toolchains where they represent different architectures or compilers and the settings that apply to one won't necessarily apply to others. 当为false(默认值)时，此工具链将不会将任何配置传播到依赖于此工具链的其他工具链中的目标。这与工具链的最常见用法相匹配，它们表示不同的架构或编译器，适用于一个的设置不一定适用于其他的。 When true, configs (public and all-dependent) will cross the boundary out of this toolchain as if the toolchain boundary wasn't there. This only affects one direction of dependencies: a toolchain can't control whether it accepts such configs, only whether it pushes them. The build is responsible for ensuring that any external targets depending on targets in this toolchain are compatible with the compiler flags, etc. that may be propagated. 当为true时，configs(公共的和所有依赖的)将跨越这个工具链的边界，就好像工具链的边界不存在一样。这只影响依赖的一个方向:工具链不能控制是否接受这些配置，只能控制是否推送它们。构建负责确保任何依赖于此工具链中的目标的外部目标与可能传播的编译器标志等兼容。  deps [string list] Dependencies of this toolchain. These dependencies will be resolved before any target in the toolchain is compiled. To avoid circular dependencies these must be targets defined in another toolchain. 此工具链的依赖关系。在编译工具链中的任何目标之前，将解析这些依赖项。为了避免循环依赖，这些必须是在另一个工具链中定义的目标。 This is expressed as a list of targets, and generally these targets will always specify a toolchain: 它表示为一个目标列表，通常这些目标将始终指定一个工具链: python deps = [ "//foo/bar:baz(//build/toolchain:bootstrap)" ]  This concept is somewhat inefficient to express in Ninja (it requires a lot of duplicate of rules) so should only be used when absolutely necessary. 这个概念在Ninja中表达起来有些低效(它需要大量规则的重复)，所以应该只在绝对必要的时候使用  Example of defining a toolchain java toolchain("32") { tool("cc") { command = "gcc " ... } toolchain_args = { use_doom_melon = true # Doom melon always required for 32-bit builds. current_cpu = "x86" } } toolchain("64") { tool("cc") { command = "gcc " ... } toolchain_args = { # use_doom_melon is not overridden here, it will take the default. current_cpu = "x64" } }   Example of cross-toolchain dependencies If a 64-bit target wants to depend on a 32-bit binary, it would specify a dependency using data_deps (data deps are like deps that are only needed at runtime and aren’t linked, since you can’t link a 32-bit and a 64-bit library). 如果一个64位目标希望依赖于一个32位二进制文件，它将使用data_deps指定一个依赖项(数据deps类似于只在运行时需要的deps，并且没有链接，因为您不能链接32位库和64位库)。 java executable("my_program") { ... if (target_cpu == "x64") { # The 64-bit build needs this 32-bit helper. data_deps = [ ":helper(//toolchains:32)" ] } } if (target_cpu == "x86") { # Our helper library is only compiled in 32-bits. shared_library("helper") { ... } }   ## target target: Declare an target with the given programmatic type. target: 用给定的程序化类型声明一个目标 python target(target_type_string, target_name_string) { ... }   The target() function is a way to invoke a built-in target or template with a type determined at runtime. This is useful for cases where the type of a target might not be known statically. target()函数是一种调用内置目标或模板的方法，其类型在运行时确定。这对于目标的类型可能不是静态已知的情况下很有用。 Only templates and built-in target functions are supported for the target_type_string parameter. Arbitrary functions, configs, and toolchains are not supported. target_type_string参数只支持模板和内置目标函数。不支持任意的函数、配置和工具链。 调用 python target("source_set", "doom_melon") {  相当于 python source_set("doom_melon") {   Example java if (foo_build_as_shared) { my_type = "shared_library" } else { my_type = "source_set" } target(my_type, "foo") { ... }   # 语法 Language and grammar for GN build files Tokens 符号 GN build files are read as sequences of tokens. While splitting the file into tokens, the next token is the longest sequence of characters that form a valid token. GN构建文件被读取为符号序列。当将文件分割为多个令牌时，下一个令牌是组成有效令牌的最长字符序列。 White space and comments White space is comprised of spaces (U+0020), horizontal tabs (U+0009), carriage returns (U+000D), and newlines (U+000A). Comments start at the character “#” and stop at the next newline. White space and comments are ignored except that they may separate tokens that would otherwise combine into a single token. 空格和注释会被忽略，除非它们可以将组合成单个标记的标记分开 Identifiers Identifiers name variables and functions.  identifier = letter { letter | digit } . letter = "A" ... "Z" | "a" ... "z" | "_" . digit = "0" ... "9" .  Keywords The following keywords are reserved and may not be used as identifiers:  else false if true  Integer literals An integer literal represents a decimal integer value.  integer = [ "-" ] digit { digit } .  Leading zeros and negative zero are disallowed. String literals A string literal represents a string value consisting of the quoted characters with possible escape sequences and variable expansions. 字符串字面值表示由带引号的字符和可能的转义序列和变量扩展组成的字符串值  string = " { char | escape | expansion } " . escape = \ ( "$" | " | char ) .
BracketExpansion = "{" ( identifier | ArrayAccess | ScopeAccess "
") "}" .
Hex              = "0x" [0-9A-Fa-f][0-9A-Fa-f]
expansion        = "$" ( identifier | BracketExpansion | Hex ) . char = /* any character except "$", ", or newline "
"*/ .


After a backslash, certain sequences represent special characters:

      \"    U+0022    quotation mark
\$U+0024 dollar sign \\ U+005C backslash  All other backslashes represent themselves. To insert an arbitrary byte value, use$0xFF. For example, to insert a newline character: “Line one$0x0ALine two”. An expansion will evaluate the variable following the ‘$’ and insert a stringified version of it into the result. For example, to concat two path components with a slash separating them: “$var_one/$var_two” Use the “${var_one}” format to be explicitly deliniate the variable for otherwise-ambiguous cases. Punctuation The following character sequences represent punctuation:  + += == != ( ) - -= < <= [ ] ! = > >= { } && || . ,  Grammar The input tokens form a syntax tree following a context-free grammar:  File = StatementList . Statement = Assignment | Call | Condition . LValue = identifier | ArrayAccess | ScopeAccess . Assignment = LValue AssignOp Expr . Call = identifier "(" [ ExprList ] ")" [ Block ] . Condition = "if" "(" Expr ")" Block [ "else" ( Condition | Block ) ] . Block = "{" StatementList "}" . StatementList = { Statement } . ArrayAccess = identifier "[" Expr "]" . ScopeAccess = identifier "." identifier . Expr = UnaryExpr | Expr BinaryOp Expr . UnaryExpr = PrimaryExpr | UnaryOp UnaryExpr . PrimaryExpr = identifier | integer | string | Call | ArrayAccess | ScopeAccess | Block | "(" Expr ")" | "[" [ ExprList [ "," ] ] "]" . ExprList = Expr { "," Expr } . AssignOp = "=" | "+=" | "-=" . UnaryOp = "!" . BinaryOp = "+" | "-" // highest priority | "<" | "<=" | ">" | ">=" | "==" | "!=" | "&&" | "||" . // lowest priority  All binary operators are left-associative. Types The GN language is dynamically typed. The following types are used: • Boolean: Uses the keywords “true” and “false”. There is no implicit conversion between booleans and integers. • Integers: All numbers in GN are signed 64-bit integers. • Strings: Strings are 8-bit with no enforced encoding. When a string is used to interact with other systems with particular encodings (like the Windows and Mac filesystems) it is assumed to be UTF-8. See “String literals” above for more. • Lists: Lists are arbitrary-length ordered lists of values. See “Lists” below for more. • Scopes: Scopes are like dictionaries that use variable names for keys. See “Scopes” below for more. — 领域: 领域类似于使用变量名作为键的字典。详见下面的“Scopes”。 Lists Lists are created with [] and using commas to separate items:  mylist = [ 0, 1, 2, "some string" ]  A comma after the last item is optional. Lists are dereferenced using 0-based indexing:  mylist[0] += 1 var = mylist[2]  Lists can be concatenated using the ‘+’ and ‘+=’ operators. Bare values can not be concatenated with lists, to add a single item, it must be put into a list of length one. Items can be removed from lists using the ‘-‘ and ‘-=’ operators. This will remove all occurrences of every item in the right-hand list from the left-hand list. It is an error to remove an item not in the list. This is to prevent common typos and to detect dead code that is removing things that no longer apply. It is an error to use ‘=’ to replace a nonempty list with another nonempty list. This is to prevent accidentally overwriting data when in most cases ‘+=’ was intended. To overwrite a list on purpose, first assign it to the empty list: mylist = [] mylist = otherlist  When assigning to a list named ‘sources’ using ‘=’ or ‘+=’, list items may be automatically filtered out. See “gn help set_sources_assignment_filter” for more. Scopes All execution happens in the context of a scope which holds the current state (like variables). With the exception of loops and conditions, ‘{‘ introduces a new scope that has a parent reference to the old scope. 所有的执行都发生在保存当前状态的作用域的上下文中(比如变量)。除了循环和条件之外，’{‘引入了一个对旧作用域具有父引用的新作用域。 Variable reads recursively search all nested scopes until the variable is found or there are no more scopes. Variable writes always go into the current scope. This means that after the closing ‘}’ (again excepting loops and conditions), all local variables will be restored to the previous values. This also means that “foo = foo” can do useful work by copying a variable into the current scope that was defined in a containing scope. 变量读取递归搜索所有嵌套作用域，直到找到变量或不再有作用域。变量写操作总是进入当前作用域。这意味着在关闭’}’之后(同样排除循环和条件)，所有局部变量都将恢复到之前的值。这也意味着”foo = foo”可以通过将变量复制到包含作用域中定义的当前作用域中来完成有用的工作。 Scopes can also be assigned to variables. Such scopes can be created by functions like exec_script, when invoking a template (the template code refers to the variables set by the invoking code by the implicitly-created “invoker” scope), or explicitly like: 作用域也可以分配给变量。这样的作用域可以在调用模板(模板代码引用调用代码通过隐式创建的”invoker”作用域设置的变量)时由像exec_script这样的函数创建，也可以显式地像: empty_scope = {} myvalues = { foo = 21 bar = "something" }  Inside such a scope definition can be any GN code including conditionals and function calls. After the close of the scope, it will contain all variables explicitly set by the code contained inside it. After this, the values can be read, modified, or added to: 在这样的作用域定义中可以包含任何GN代码，包括条件和函数调用。在作用域关闭之后，它将包含由其中包含的代码显式设置的所有变量。在此之后，可以读取、修改或添加这些值: myvalues.foo += 2 empty_scope.new_thing = [ 1, 2, 3 ]  Scope equality is defined as single-level scopes identical within the current scope. That is, all values in the first scope must be present and identical within the second, and vice versa. Note that this means inherited scopes are always unequal by definition. 作用域相等定义为当前作用域内相同的单层作用域。也就是说，第一个作用域中的所有值必须出现，并且在第二个作用域中相同，反之亦然。注意，这意味着继承的作用域根据定义总是不相等的。 ## .gn 文件 When gn starts, it will search the current directory and parent directories for a file called “.gn”. This indicates the source root. You can override this detection by using the –root command-line argument gn启动时，它将在当前目录和父目录中搜索名为“.gn”的文件。这表示源根目录。您可以使用–root命令行参数覆盖此检测 The .gn file in the source root will be executed. The syntax is the same as a buildfile, but with very limited build setup-specific meaning. 这个将执行源根目录中的gn文件。语法与构建文件相同，但具有非常有限的构建设置特定含义 If you specify –root, by default GN will look for the file .gn in that directory. If you want to specify a different file, you can additionally pass –dotfile: 如果指定–root，默认情况下，GN将在那个目录中查找该.gn文件。如果要指定其他文件，还可以传递–dotfile： gn gen out/Debug --root=/home/build --dotfile=/home/my_gn_file.gn  Example .gn file contents buildconfig = "//build/config/BUILDCONFIG.gn" check_targets = [ "//doom_melon/*", # Check everything in this subtree. "//tools:mind_controlling_ant", # Check this specific target. ] root = "//:root" secondary_source = "//build/config/temporary_buildfiles/" default_args = { # Default to release builds for this project. is_debug = false is_component_build = false }  ### check_targets [optional] A list of labels and label patterns that should be checked when running “gn check” or “gn gen –check”. If unspecified, all targets will be checked. If it is the empty list, no targets will be checked. To bypass this list, request an explicit check of targets, like “//*”. 运行“gn check”或“gn gen–check”时应检查的标签和标签模板列表。如果未指定，将检查所有目标。如果是空列表，则不会检查任何目标。要绕过此列表，请请求显式检查目标，如“//*”。 The format of this list is identical to that of “visibility” so see “gn help visibility” for examples. 此列表的格式与“可见性”的格式相同，因此请参见“gn help visibility”以获取示例。 ## group group: Declare a named group of targets. group：声明一组命名的目标 This target type allows you to create meta-targets that just collect a set of dependencies into one named target. Groups can additionally specify configs that apply to their dependents. 此目标类型允许您创建只将一组依赖项收集到一个命名目标中的元目标。组还可以指定应用于其从属项的配置。 Variables Deps: data_deps, deps, public_deps Dependent configs: all_dependent_configs, public_configs Example group("all") { deps = [ "//project:runner", "//project:unit_tests", ] }  ## shared_library Declare a shared library target. A shared library will be specified on the linker line for targets listing the shared library in its “deps”. If you don’t want this (say you dynamically load the library at runtime), then you should depend on the shared library via “data_deps” or, on Darwin platforms, use a “loadable_module” target type instead. 共享库将在链接器行中指定，目标将在其“deps”中列出共享库。如果您不希望这样(假设您在运行时动态加载库)，那么您应该通过“data_deps”依赖于共享库，或者，在Darwin平台上，使用“loadable_module”目标类型。 Language and compilation 语言和编译 The tools and commands used to create this target type will be determined by the source files in its sources. Targets containing multiple compiler-incompatible languages are not allowed (e.g. a target containing both C and C++ sources is acceptable, but a target containing C and Rust sources is not). 用于创建此目标类型的工具和命令将由其源文件中的源文件决定。不允许目标包含多个编译器不兼容的语言(例如，包含C和c++源的目标是可以接受的，但包含C和Rust源的目标是不允许的)。 Variables Flags: cflags, cflags_c, cflags_cc, cflags_objc, cflags_objcc, asmflags, defines, include_dirs, inputs, ldflags, lib_dirs, libs, precompiled_header, precompiled_source, rustflags, rustenv Deps: data_deps, deps, public_deps Dependent configs: all_dependent_configs, public_configs General: check_includes, configs, data, friend, inputs, metadata, output_name, output_extension, public, sources, testonly, visibility Rust variables: aliased_deps, crate_root, crate_name, crate_type ## rebase_path Rebase a file or directory to another location. 将文件或目录重设为另一个位置 converted = rebase_path(input, new_base = "", current_base = ".")  Takes a string argument representing a file name, or a list of such strings and converts it/them to be relative to a different base directory. 接受表示文件名或此类字符串列表的字符串参数，并将其/它们转换为相对于不同的基目录 When invoking the compiler or scripts, GN will automatically convert sources and include directories to be relative to the build directory. However, if you’re passing files directly in the “args” array or doing other manual manipulations where GN doesn’t know something is a file name, you will need to convert paths to be relative to what your tool is expecting. 在调用编译器或脚本时，GN会自动将源文件和包含文件的目录转换为相对于构建目录的目录。然而，如果你在 “args”数组中直接传递文件，或做其他手工操作，而GN不知道某样东西是一个文件名，你将需要把路径转换成相对于你的工具所期望的。 The common case is to use this to convert paths relative to the current directory to be relative to the build directory (which will be the current directory when executing scripts). 常见的情况是用它将相对于当前目录的路径转换为相对于构建目录的路径（执行脚本时，它将是当前目录）。 If you want to convert a file path to be source-absolute (that is, beginning with a double slash like “//foo/bar”), you should use the get_path_info() function. This function won’t work because it will always make relative paths, and it needs to support making paths relative to the source root, so can’t also generate source-absolute paths without more special-cases. 如果你想把文件路径转换为源绝对路径（即以双斜线开始，如”//foo/bar”），你应该使用get_path_info()函数。这个函数不能工作，因为它总是生成相对路径，而且它需要支持生成相对于源根的路径，所以如果没有更多的特殊情况，就不能生成源绝对路径。 Arguments input A string or list of strings representing file or directory names These can be relative paths (“foo/bar.txt”), system absolute paths (“/foo/bar.txt”), or source absolute paths (“//foo/bar.txt”). 代表文件或目录名称的字符串或字符串列表 这些可以是相对路径（”foo/bar.txt”），系统绝对路径（”/foo/bar.txt”），或源绝对路径（”//foo/bar.txt”）。 new_base The directory to convert the paths to be relative to. This can be an absolute path or a relative path (which will be treated as being relative to the current BUILD-file’s directory). 要将路径转换为相对路径的目录。这可以是一个绝对路径或相对路径（将被视为相对于当前BUILD-file的目录）。 As a special case, if new_base is the empty string (the default), all paths will be converted to system-absolute native style paths with system path separators. This is useful for invoking external programs. 作为一种特殊情况，如果new_base是空字符串（默认），所有路径将被转换为带有系统路径分隔符的系统绝对本地风格路径。这对于调用外部程序很有用。 current_base Directory representing the base for relative paths in the input. If this is not an absolute path, it will be treated as being relative to the current build file. Use “.” (the default) to convert paths from the current BUILD-file’s directory. 代表输入中相对路径的基础的目录。如果这不是一个绝对路径，它将被视为是相对于当前构建文件的。使用”.”（默认）来转换来自当前BUILD-文件目录的路径。 Return value The return value will be the same type as the input value (either a string or a list of strings). All relative and source-absolute file names will be converted to be relative to the requested output System-absolute paths will be unchanged. 返回值将与输入值的类型相同（字符串或字符串列表）。所有相对的和源绝对值的文件名将被转换为与请求的输出相对的系统绝对值路径将不会改变。 Whether an output path will end in a slash will match whether the corresponding input path ends in a slash. It will return “.” or “./” (depending on whether the input ends in a slash) to avoid returning empty strings. This means if you want a root path (“//” or “/”) not ending in a slash, you can add a dot (“//.”). 一个输出路径是否以斜线结尾，将与相应的输入路径是否以斜线结尾相匹配。它将返回”. “或”./” (取决于输入是否以斜线结尾）以避免返回空字符串。这意味着如果你想要一个不以斜线结尾的根路径（”//”或”/”），你可以添加一个点（”//。”）。 Example # Convert a file in the current directory to be relative to the build directory (the current dir when executing compilers and scripts). # 将当前目录下的文件转换为与构建目录（执行编译器和脚本时的当前目录）的相对关系 foo = rebase_path("myfile.txt", root_build_dir) # might produce "../../project/myfile.txt". # Convert a file to be system absolute: foo = rebase_path("myfile.txt") # Might produce "D:\\source\\project\\myfile.txt" on Windows or # "/home/you/source/project/myfile.txt" on Linux. # Typical usage for converting to the build directory for a script. action("myscript") { # Don't convert sources, GN will automatically convert these to be relative to the build directory when it constructs the command line for your script. # 不要转换源码，GN在为你的脚本构建命令行时，会自动将这些源码转换为相对的构建目录 sources = [ "foo.txt", "bar.txt" ] # Extra file args passed manually need to be explicitly converted to be relative to the build directory: # 手动传递的额外文件参数需要明确转换为相对于构建目录的参数。 args = [ "--data", rebase_path("//mything/data/input.dat", root_build_dir), "--rel", rebase_path("relative_path.txt", root_build_dir) ] + rebase_path(sources, root_build_dir) }  ## root_build_dir: [string] Directory where build commands are run. 运行构建命令的目录 This is the root build output directory which will be the current directory when executing all compilers and scripts. 这是根构建输出目录，在执行所有编译器和脚本时，它将是当前目录。 Most often this is used with rebase_path (see “gn help rebase_path”) to convert arguments to be relative to a script’s current directory. 最常见的是与 rebase_path（见 “gn help rebase_path”）一起使用，将参数转换为相对于脚本的当前目录。 ## tool tool: Specify arguments to a toolchain tool. tool:为工具链工具指定参数 Usage tool(<tool type>) { <tool variables...> }  Tool types Compiler tools: "cc": C compiler "cxx": C++ compiler "objc": Objective C compiler "objcxx": Objective C++ compiler "rc": Resource compiler (Windows .rc files) "asm": Assembler Linker tools: "alink": Linker for static libraries (archives) "solink": Linker for shared libraries "link": Linker for executables Other tools: "stamp": Tool for creating stamp files "copy": Tool to copy files. "action": Defaults for actions Platform specific tools: "copy_bundle_data": [iOS, macOS] Tool to copy files in a bundle. "compile_xcassets": [iOS, macOS] Tool to compile asset catalogs. Rust tools: "rust_bin": Tool for compiling Rust binaries "rust_cdylib": Tool for compiling C-compatible dynamic libraries. "rust_dylib": Tool for compiling Rust dynamic libraries. "rust_macro": Tool for compiling Rust procedural macros. "rust_rlib": Tool for compiling Rust libraries. "rust_staticlib": Tool for compiling Rust static libraries.  Tool variables command [string with substitutions] Valid for: all tools except "action" (required) 适用于:除“action”之外的所有工具(必需的) The command to run. 要运行的命令 command_launcher [string] Valid for: all tools except "action" (optional) The prefix with which to launch the command (e.g. the path to a Goma or CCache compiler launcher). 用于启动命令的前缀(例如，Goma或CCache编译器启动器的路径)。 Note that this prefix will not be included in the compilation database or IDE files generated from the build. 请注意，这个前缀不会包含在编译数据库或生成的IDE文件中 default_output_dir [string with substitutions] Valid for: linker tools Default directory name for the output file relative to the root_build_dir. It can contain other substitution patterns. This will be the default value for the expansion (discussed below) but will be overridden by the "output_dir" variable in a target, if one is specified. 输出文件相对于root_build_dir的默认目录名。它可以包含其他替换模式。这将是展开的默认值(下面将讨论)，但如果指定了目标变量，则会被“output_dir”变量覆盖。 GN doesn't do anything with this string other than pass it along, potentially with target-specific overrides. It is the tool's job to use the expansion so that the files will be in the right place. GN对该字符串不做任何操作，只是传递它，可能使用特定于目标的覆盖。该工具的工作是使用展开，以便文件将位于正确的位置。 default_output_extension [string] Valid for: linker tools Extension for the main output of a linkable tool. It includes the leading dot. This will be the default value for the expansion (discussed below) but will be overridden by by the "output extension" variable in a target, if one is specified. Empty string means no extension. 可链接工具的主要输出的扩展。它包括前导点。这将是扩展(下面将讨论)的默认值，但如果指定了目标变量，则会被“output extension”变量覆盖。空字符串意味着没有扩展名。 GN doesn't actually do anything with this extension other than pass it along, potentially with target-specific overrides. One would typically use the value in the "outputs" to read this value. GN实际上对这个扩展不做任何事情，只是传递它，可能与目标特定的覆盖。通常使用“output”中的值来读取该值。 Example: default_output_extension = ".exe" depfile [string with substitutions] Valid for: compiler tools (optional) If the tool can write ".d" files, this specifies the name of the resulting file. These files are used to list header file dependencies (or other implicit input dependencies) that are discovered at build time. See also "depsformat". 如果工具可以写”.d"文件，这指定了结果文件的名称。这些文件用于列出在构建时发现的头文件依赖项(或其他隐式输入依赖项)。参见“depsformat”。 Example: depfile = ".d" depsformat [string] Valid for: compiler tools (when depfile is specified) Format for the deps outputs. This is either "gcc" or "msvc". See the ninja documentation for "deps" for more information. deps输出的格式。这是"gcc"或"msvc"。有关更多信息，请参阅忍者文档“deps” Example: depsformat = "gcc" description [string with substitutions, optional] Valid for: all tools What to print when the command is run. 运行命令时要打印的内容。 Example: description = "Compiling " exe_output_extension [string, optional, rust tools only] rlib_output_extension [string, optional, rust tools only] dylib_output_extension [string, optional, rust tools only] cdylib_output_extension [string, optional, rust tools only] rust_proc_macro_output_extension [string, optional, rust tools only] Valid for: Rust tools These specify the default tool output for each of the crate types. The default is empty for executables, shared, and static libraries and ".rlib" for rlibs. Note that the Rust compiler complains with an error if external crates do not take the form lib<name>.rlib or lib<name>.<shared_extension>, where <shared_extension> is .so, .dylib, or .dll as appropriate for the platform. 这些指定了每个carte类型的默认工具输出。 对于可执行文件、共享库和静态库，默认为空，对于rlibs，默认为".rlib"。请注意，如果外部板条箱不采用lib<name>.rlib或lib<name>.<shared_extension>的形式，Rust编译器会报错，其中<shared_extension>是.so、.dylib或.dll，根据平台的情况而定。 lib_switch [string, optional, link tools only] lib_dir_switch [string, optional, link tools only] Valid for: Linker tools except "alink" These strings will be prepended to the libraries and library search directories, respectively, because linkers differ on how to specify them. 这些字符串将分别被预置到库和库搜索目录中，因为链接器在如何指定它们方面存在差异。 If you specified: lib_switch = "-l" lib_dir_switch = "-L" then the "" expansion for [ "freetype", "expat" ] would be "-lfreetype -lexpat". framework_switch [string, optional, link tools only] framework_dir_switch [string, optional, link tools only] Valid for: Linker tools These strings will be prepended to the frameworks and framework search path directories, respectively, because linkers differ on how to specify them. 这些字符串将分别被预置到框架和框架搜索路径目录中，因为链接器在如何指定它们方面有所不同。 If you specified: framework_switch = "-framework " framework_dir_switch = "-F" then the "" expansion for [ "UIKit.framework", "$root_out_dir/Foo.framework" ]
would be
"-framework UIKit -F. -framework Foo"

outputs  [list of strings with substitutions]
Valid for: Linker and compiler tools (required)

An array of names for the output files the tool produces. These are relative to the build output directory. There must always be at least one output file. There can be more than one output (a linker might produce a library and an import library, for example).

该工具产生的输出文件的名称数组。这些是相对于构建输出目录的。总是必须至少有一个输出文件。可以有一个以上的输出（例如，一个链接器可能产生一个库和一个导入库）。

This array just declares to GN what files the tool will produce. It is your responsibility to specify the tool command that actually produces these files.

这个数组只是向GN声明该工具将产生哪些文件。你有责任指定实际产生这些文件的工具命令。

If you specify more than one output for shared library links, you should consider setting link_output, depend_output, and runtime_outputs.

Example for a compiler tool that produces .obj files:

一个产生.obj文件的编译工具的例子。

outputs = [
"/.obj"
]

Example for a linker tool that produces a .dll and a .lib. The use of ,  and  allows the target to override these values.

一个链接器工具的例子，它能产生一个.dll和一个.lib。使用、和允许目标覆盖这些值。

outputs = [
"/"
"",
"/.lib",
]

pool [label, optional]
Valid for: all tools (optional)

Label of the pool to use for the tool. Pools are used to limit the
number of tasks that can execute concurrently during the build.

depend_output  [string with substitutions]

These two files specify which of the outputs from the solink tool should be used for linking and dependency tracking. These should match entries in the "outputs". If unspecified, the first item in the "outputs" array will be used for all. See "Separate linking and dependencies for shared libraries" below for more.

On Windows, where the tools produce a .dll shared library and a .lib import library, you will want the first two to be the import library and the third one to be the .dll file. On Linux, if you're not doing the separate linking/dependency optimization, all of these should be the .so output.

在Windows上，工具会产生一个.dll共享库和一个.lib导入库，你会希望前两个是导入库，第三个则是.dll文件。在Linux上，如果你不做单独的链接/依赖性优化，所有这些都应该是.so的输出。

output_prefix  [string]

Prefix to use for the output name. Defaults to empty. This prefix will be prepended to the name of the target (or the output_name if one is manually specified for it) if the prefix is not already there. The result will show up in the  substitution pattern.

用于输出名称的前缀。默认为空。如果目标名称中没有前缀，该前缀将被添加到目标名称中（或者如果手动指定了output_name）。其结果将显示在的替换模式中。

Individual targets can opt-out of the output prefix by setting:
output_prefix_override = true
(see "gn help output_prefix_override").

This is typically used to prepend "lib" to libraries on
Posix systems:
output_prefix = "lib"

Valid for: "cc", "cxx", "objc", "objcxx"

Type of precompiled headers. If undefined or the empty string, precompiled headers will not be used for this tool. Otherwise use "gcc" or "msvc".

预编译头文件的类型。如果未定义或为空字符串，预编译头文件将不被用于该工具。否则使用 "gcc "或 "msvc"。

For precompiled headers to be used for a given target, the target (or a
config applied to it) must also specify a "precompiled_header" and, for
"msvc"-style headers, a "precompiled_source" value. If the type is
"gcc", then both "precompiled_header" and "precompiled_source" must
resolve to the same file, despite the different formats required for
each."

See "gn help precompiled_header" for more.

restat  [boolean]
Valid for: all tools (optional, defaults to false)

Requests that Ninja check the file timestamp after this tool has run to determine if anything changed. Set this if your tool has the ability to skip writing output if the output file has not changed.

请求忍者在此工具运行后检查文件的时间戳，以确定是否有任何更改。如果您的工具能够在输出文件没有更改的情况下跳过写入输出，则设置此选项。

Normally, Ninja will assume that when a tool runs the output be new and downstream dependents must be rebuild. When this is set to trye, Ninja can skip rebuilding downstream dependents for input changes that don't actually affect the output.

通常情况下，Ninja会认为当一个工具运行时，输出是新的，下游的依赖必须重建。当这个选项被设置为trye时，Ninja可以跳过重建对输出没有实际影响的输入依赖关系。

Example:
restat = true

rspfile  [string with substitutions]
Valid for: all tools except "action" (optional)

Name of the response file. If empty, no response file will be used. See "rspfile_content".

响应文件的名称。如果为空，则不使用响应文件。看到“rspfile_content”。

rspfile_content  [string with substitutions]
Valid for: all tools except "action" (required when "rspfile" is used)

The contents to be written to the response file. This may include all or part of the command to send to the tool which allows you to get around OS command-line length limits.

要写入响应文件的内容。这可能包括要发送给工具的全部或部分命令，这允许您绕过操作系统命令行长度限制。

This example adds the inputs and libraries to a response file, but passes the linker flags directly on the command line:

这个例子将输入和库添加到响应文件中，但直接在命令行上传递链接器标志:

rspfile = ".rsp"
rspfile_content = "  "
}

runtime_outputs  [string list with substitutions]

If specified, this list is the subset of the outputs that should be added to runtime deps (see "gn help runtime_deps"). By default (if runtime_outputs is empty or unspecified), it will be the link_output.



Expansions for tool variables

All paths are relative to the root build directory, which is the current directory for running all tools. These expansions are available to all tools:

    The label of the current target. This is typically used in the "description" field for link tools. The toolchain will be omitted from the label for targets in the default toolchain, and will be included for targets in other toolchains.

当前目标的标签。这通常用于链接工具的“描述”字段。工具链将从默认工具链中的目标的标签中省略，并将在其他工具链中的目标中包含。

The short name of the label of the target. This is the part after the colon. For "//foo/bar:baz" this will be "baz". Unlike , this is not affected by the "output_prefix" in the tool or the "output_name" set on the target.

目标器标签的短名称。这是":"后面的部分。对于"//foo/bar:baz"，这将是"baz"。与不同，它不受工具中的“output_prefix”或目标上设置的“output_name”的影响。

The relative path and name of the output(s) of the current build step.  If there is more than one output, this will expand to a list of all of them. Example: "out/base/my_file.o"

当前构建步骤的输出的相对路径和名称。如果有多个输出，则将扩展为所有输出的列表。

示例: "out/base/my_file.o"

The directory of the generated file and output directories, respectively, for the current target. There is no trailing slash. See also  for linker tools. Example: "out/base/test"

生成文件的目录和输出目录，分别为当前目标。没有尾随斜杠。链接器工具参见。

例如: "out/base/test"

The short name of the current target with no path information, or the value of the "output_name" variable if one is specified in the target.  This will include the "output_prefix" if any. See also .

不带路径信息的当前目标的短名称，如果目标中指定了“output_name”变量，则为该变量的值。如果有的话，这将包括“output_prefix”。参见。

Example: "libfoo" for the target named "foo" and an output prefix for the linker tool of "lib".

例如:目标名为“foo”的目标为“libfoo”，连接器工具的输出前缀为“lib”。


Compiler tools have the notion of a single input and a single output, along with a set of compiler-specific flags. The following expansions are available:

    Strings correspond that to the processed flags/defines/include directories specified for the target.

字符串对应于为目标指定的已处理的flags/defines/include目录

Example: "--enable-foo --enable-bar"

Defines will be prefixed by "-D" and include directories will be prefixed by "-I" (these work with Posix tools as well as Microsoft ones).

定义的前缀是"-D"，包含的目录的前缀是"-I"（这些在Posix工具和微软的工具上都能使用）。

The relative path and name of the current input file.

当前输入文件的相对路径和名称。

Example: "../../base/my_file.cc"

The file part of the source including the extension (with no directory information).

source的文件部分，包括扩展名（没有目录信息）。

Example: "foo.cc"

The filename part of the source file with no directory or extension.
Example: "foo"

The directory in the generated file and output directories, respectively, for the current input file. If the source file is in the same directory as the target is declared in, they will will be the same as the "target" versions above. Example: "gen/base/test"

生成文件和输出目录中的目录，分别为当前输入文件。如果源文件与目标文件声明在同一目录下，它们将与上面的 "目标 "版本相同。例如。"gen/base/test"


Linker tools have multiple inputs and (potentially) multiple outputs. The static library tool (“alink”) is not considered a linker tool. The following expansions are available:

    Expands to the inputs to the link step. This will be a list of object files and static libraries.
Example: "obj/foo.o obj/bar.o obj/somelibrary.a"

扩展到链接步骤的输入。这将是一个对象文件和静态库的列表。
例如。"obj/foo.o obj/bar.o obj/somelibrary.a"

The "_newline" version will separate the input files with newlines instead of spaces. This is useful in response files: some linkers can take a "-filelist" flag which expects newline separated files, and some Microsoft tools have a fixed-sized buffer for parsing each line of a response file.

"_newline "版本将用换行符而不是空格来分隔输入文件。这在响应文件中很有用：一些链接器可以使用"-filelist "标志，期望用换行符分隔文件，一些微软工具有一个固定大小的缓冲区来解析响应文件的每一行。

Expands to the processed set of ldflags and library search paths specified for the target.

扩展到为目标指定的ldflags和库搜索路径的处理集

Expands to the list of system libraries to link to. Each will be prefixed by the "lib_switch".

扩展到要链接的系统库的列表。每一个都将以 "lib_switch "为前缀。

As a special case to support Mac, libraries with names ending in ".framework" will be added to the  with "-framework" preceding it, and the lib prefix will be ignored.

作为支持Mac的特殊情况，名称以".framework "结尾的库将被添加到中，前面是"-framework"，而lib前缀将被忽略。

Example: "-lfoo -lbar"

The value of the "output_dir" variable in the target, or the the value of the "default_output_dir" value in the tool if the target does not override the output directory. This will be relative to the root_build_dir and will not end in a slash. Will be "." for output to the root_build_dir.

目标中 "output_dir "变量的值，如果目标没有覆盖输出目录，则是工具中 "default_output_dir "的值。这将是相对于root_build_dir的，不会以斜线结尾。对于输出到root_build_dir，将是"."。

This is subtly different than  which is defined by GN based on the target's path and not overridable.  is for the final output,  is generally for object files and other outputs.

这与有细微的不同，后者是由GN根据目标的路径定义的，不可重写。用于最终输出，一般用于对象文件和其他输出。

Usually  would be defined in terms of either  or

通常，会被定义为或的一部分。

The value of the "output_extension" variable in the target, or the value of the "default_output_extension" value in the tool if the target does not specify an output extension.

目标中 "output_extension "变量的值，如果目标没有指定输出扩展，则是工具中 "default_output_extension "的值。

Example: ".so"

Extra libraries from shared library dependencies not specified in the
. This is the list of link_output files from shared libraries
the "depend_output").

These should generally be treated the same as libs by your tool.

Example: "libfoo.so libbar.so"

Shared libraries packaged as framework bundle. This is principally
used on Apple's platforms (macOS and iOS). All name must be ending
with ".framework" suffix; the suffix will be stripped when expanding
and each item will be preceded by "-framework".


The static library (“alink”) tool allows plus the common tool substitutions.

The copy tool allows the common compiler/linker substitutions, plus which is the source of the copy. The stamp tool allows only the common tool substitutions.

The copy_bundle_data and compile_xcassets tools only allows the common tool substitutions. Both tools are required to create iOS/macOS bundles and need only be defined on those platforms.

copy_bundle_data和compile_xcassets工具只允许常用的工具替换。这两个工具都是创建iOS/MacOS捆绑包所需要的，只需要在这些平台上定义。

The copy_bundle_data tool will be called with one source and needs to copy (optionally optimizing the data representation) to its output. It may be called with a directory as input and it needs to be recursively copied.

The compile_xcassets tool will be called with one or more source (each an asset catalog) that needs to be compiled to a single output. The following substitutions are available:

    Expands to the list of .xcassets to use as input to compile the asset catalog.

Expands to the product_type of the bundle that will contain the
compiled asset catalog. Usually corresponds to the product_type
property of the corresponding create_bundle target.

Expands to the path to the partial Info.plist generated by the
assets catalog compiler. Usually based on the target_name of
the create_bundle target.


Rust tools have the notion of a single input and a single output, along with a set of compiler-specific flags. The following expansions are available:

    Expands to the string representing the crate name of target under
compilation.

Expands to the string representing the type of crate for the target
under compilation.

Expands to the list of --extern flags needed to include addition Rust
libraries in this target. Includes any specified renamed dependencies.

Expands to the list of -Ldependency=<path> strings needed to compile
this target.

Expands to the list of environment variables.

Expands to the list of strings representing Rust compiler flags.


Separate linking and dependencies for shared libraries

Shared libraries are special in that not all changes to them require that dependent targets be re-linked. If the shared library is changed but no imports or exports are different, dependent code needn’t be relinked, which can speed up the build.

If your link step can output a list of exports from a shared library and writes the file only if the new one is different, the timestamp of this file can be used for triggering re-links, while the actual shared library would be used for linking.

You will need to specify restat = true in the linker tool to make this work, so Ninja will detect if the timestamp of the dependency file has changed after linking (otherwise it will always assume that running a command updates the output):

tool("solink") {
command = "..."
outputs = [
"/",
"/"
".TOC",
]
"/"
depend_output =
"/"
".TOC"
restat = true
}


Example

toolchain("my_toolchain") {
# Put these at the top to apply to all tools below.
# 把这些放在顶部，适用于下面的所有工具。
lib_switch = "-l"
lib_dir_switch = "-L"

tool("cc") {
command = "gcc  -o "
outputs = [ "/.o" ]
description = "GCC "
}
tool("cxx") {
command = "g++  -o "
outputs = [ "/.o" ]
description = "G++ "
}
};


## dotfile

.gn file

When gn starts, it will search the current directory and parent directories for a file called “.gn”. This indicates the source root. You can override this detection by using the –root command-line argument

The .gn file in the source root will be executed. The syntax is the same as a buildfile, but with very limited build setup-specific meaning.

If you specify –root, by default GN will look for the file .gn in that directory. If you want to specify a different file, you can additionally pass –dotfile:

gn gen out/Debug --root=/home/build --dotfile=/home/my_gn_file.gn


Variables

• arg_file_template [optional]

Path to a file containing the text that should be used as the default args.gn content when you run gn args.

当你运行gn args时，包含文本的文件应作为默认的args.gn内容，其路径。

• buildconfig [required]

Path to the build config file. This file will be used to set up the build file execution environment for each toolchain.

构建配置文件的路径。这个文件将被用来为每个工具链设置构建文件的执行环境

• check_targets [optional]

A list of labels and label patterns that should be checked when running “gn check” or “gn gen –check”. If unspecified, all targets will be checked. If it is the empty list, no targets will be checked. To bypass this list, request an explicit check of targets, like “//*”.

运行 “gn check “或 “gn gen –check “时应检查的标签和标签模式的列表。如果没有指定，所有目标都将被检查。如果它是空列表，则不会检查任何目标。要绕过这个列表，请要求明确检查目标，如”//*“。

The format of this list is identical to that of “visibility” so see “gn help visibility” for examples.

这个列表的格式与 “可见性 “的格式相同，所以请看 “gn help visibility “的例子。

• check_system_includes [optional]

Boolean to control whether system style includes are checked by default when running “gn check” or “gn gen –check”. System style includes are includes that use angle brackets <> instead of double quotes “”. If this setting is omitted or set to false, these includes will be ignored by default. They can be checked explicitly by running “gn check –check-system” or “gn gen –check=system”

布尔值用于控制在运行 “gn check “或 “gn gen –check “时是否默认检查系统风格的包含。 系统风格包含是指使用角括号<>而不是双引号”“的包含。如果这个设置被省略或设置为false，这些内容将被默认忽略。可以通过运行 “gn check –check-system “或 “gn gen –check=system “来明确检查它们。

• exec_script_whitelist [optional]

A list of .gn/.gni files (not labels) that have permission to call the exec_script function. If this list is defined, calls to exec_script will be checked against this list and GN will fail if the current file isn’t in the list.

有权限调用 exec_script 函数的 .gn/.gni 文件（不是标签）的列表。如果定义了这个列表，对exec_script的调用将根据这个列表进行检查，如果当前文件不在这个列表中，GN将失败。

This is to allow the use of exec_script to be restricted since is easy to use inappropriately. Wildcards are not supported. Files in the secondary_source tree (if defined) should be referenced by ignoring the secondary tree and naming them as if they are in the main tree.

If unspecified, the ability to call exec_script is unrestricted.

  Example:
exec_script_whitelist = [
"//base/BUILD.gn",
"//build/my_config.gni",
]


root [optional] Label of the root build target. The GN build will start by loading the build file containing this target name. This defaults to “//:” which will cause the file //BUILD.gn to be loaded.

script_executable [optional] Path to specific Python executable or other interpreter to use in action targets and exec_script calls. By default GN searches the PATH for Python to execute these scripts.

If set to the empty string, the path specified in action targets
and exec_script calls will be executed directly.


secondary_source [optional] Label of an alternate directory tree to find input files. When searching for a BUILD.gn file (or the build config file discussed above), the file will first be looked for in the source root. If it’s not found, the secondary source root will be checked (which would contain a parallel directory hierarchy).

标签的替代目录树来寻找输入文件。当搜索BUILD.gn文件（或上面讨论的构建配置文件）时，将首先在源根中寻找该文件。如果没有找到，将检查次要的源根（它将包含一个平行的目录层次结构）。

This behavior is intended to be used when BUILD.gn files can't be checked in to certain source directories for whatever reason.

这种行为旨在用于BUILD.gn文件因某种原因无法进入某些源代码目录检查的情况

The secondary source root must be inside the main source tree.


default_args [optional] Scope containing the default overrides for declared arguments. These overrides take precedence over the default values specified in the declare_args() block, but can be overriden using –args or the args.gn file.

包含声明参数的默认覆盖值的范围。这些覆盖值优先于 declare_args() 块中指定的默认值，但可以使用 --args 或 args.gn 文件来覆盖。

This is intended to be used when subprojects declare arguments with default values that need to be changed for whatever reason.

当子项目声明的参数具有默认值，但由于某种原因需要改变时，就可以使用这个方法。


Example .gn file contents

# 设置build文件的执行环境
buildconfig = "//build/config/BUILDCONFIG.gn"

check_targets = [
"//doom_melon/*",  # Check everything in this subtree.
"//tools:mind_controlling_ant",  # Check this specific target.
]

root = "//:root"

secondary_source = "//build/config/temporary_buildfiles/"

default_args = {
# Default to release builds for this project.
is_debug = false
is_component_build = false
}


## public_configs

Configs to be applied on dependents.

A list of config labels.

Targets directly depending on this one will have the configs listed in this variable added to them. These configs will also apply to the current target. Generally, public configs are used to apply defines and include directories necessary to compile this target’s header files.

Propagation of public configs

Public configs are applied to all targets that depend directly on this one. These dependant targets can further push this target’s public configs higher in the dependency tree by depending on it via public_deps (see “gn help public_deps”).

static_library("toplevel") {
# This target will get "my_config" applied to it.
# However, since this target uses "deps" and not "public_deps",
# targets that depend on this one won't get it.
# 这个目标将得到“my_config”应用到它。
# 然而，由于此目标使用“deps”而不是“public_deps”，因此依赖于此目标的目标将无法获得它。
deps = [ ":intermediate" ]
}

static_library("intermediate") {
# Depending on "lower" in any way will apply "my_config" to this target. Additionall, since this target depends on "lower" via public_deps, targets that depend on this one will also get "my_config".

# 以任何方式依赖于“lower”将“my_config”应用到这个目标
# 另外，因为这个目标依赖于“lower”通过public_deps，目标依赖于这个也会得到“my_config”。
public_deps = [ ":lower" ]
}

static_library("lower") {
# This will get applied to all targets that depend on this one.
# 这将应用于所有依赖于此的目标
public_configs = [ ":my_config" ]
}


Public config propagation happens in a second phase once a target and all of its dependencies have been resolved. Therefore, a target will not see these force-added configs in their “configs” variable while the script is running, and they can not be removed. As a result, this capability should generally only be used to add defines and include directories rather than setting complicated flags that some targets may not want.

Public configs may or may not be propagated across toolchain boundaries depending on the value of the propagates_configs flag (see “gn help toolchain”) on the toolchain of the target declaring the public_config.

Avoiding applying public configs to this target

If you want the config to apply to targets that depend on this one, but NOT this one, define an extra layer of indirection using a group:

# External targets depend on this group.
group("my_target") {
# Config to apply to all targets that depend on this one.
# Config应用于所有依赖于此的目标
public_configs = [ ":external_settings" ]
deps = [ ":internal_target" ]
}

# Internal target to actually compile the sources.
# 内部目标，以实际编译源
static_library("internal_target") {
# Force all external targets to depend on the group instead of directly on this so the "external_settings" config will get applied.
# 强制所有外部目标依赖于组，而不是直接依赖于此，因此“external_settings”配置将被应用。
visibility = [ ":my_target" ]
...
}
`

## A list of target labels

Specifies private dependencies of a target. Private dependencies are propagated up the dependency tree and linked to dependent targets, but do not grant the ability to include headers from the dependency. Public configs are not forwarded.

### Details of dependency propagation

Source sets, shared libraries, and non-complete static libraries will be propagated up the dependency tree across groups, non-complete static libraries and source sets.

Executables, shared libraries, and complete static libraries will link all propagated targets and stop propagation. Actions and copy steps also stop propagation, allowing them to take a library as an input but not force dependents to link to it.

Propagation of all_dependent_configs and public_configs happens independently of target type. all_dependent_configs are always propagated across all types of targets, and public_configs are always propagated across public deps of all types of targets.

all_dependent_configs和public_configs的传播独立于目标类型。All_dependent_configs总是跨所有类型的目标传播，而public_configs总是跨所有类型的目标的公共部门传播。

Data dependencies are propagated differently. See “gn help data_deps” and “gn help runtime_deps”.