- Uso
- Variables predefinidas
- Variables predefinidas de genrule
- Variables de ruta de origen y salida predefinidas
- Variables personalizadas
Las variables "Make" son una clase especial de variables de string expandibles disponibles para los atributos marcados como "Subject to 'Make variable' sustitution".
Se pueden usar, por ejemplo, para incorporar rutas específicas de la cadena de herramientas en las acciones de compilación creadas por el usuario.
Bazel proporciona variables predefinidas, que están disponibles para todos los destinos, y variables personalizadas, que se definen en objetivos de dependencias y solo disponibles para objetivos que dependen de ellos.
El motivo para el término "Make" es histórico: la sintaxis y la semántica de estas variables originalmente estaban destinadas a coincidir con GNU Make.
Uso
Los atributos marcados como "Sujeto a la sustitución de 'Variable de Make'" pueden hacer referencia a la variable "Make" FOO
de la siguiente manera:
my_attr = "prefix $(FOO) suffix"
En otras palabras, cualquier substring que coincida con $(FOO)
se expande al valor de FOO
. Si ese valor es "bar"
, la string final pasa a ser la siguiente:
my_attr = "prefix bar suffix"
Si FOO
no corresponde a una variable conocida por el destino de consumo, Bazel falla con un error.
Las variables "Make" cuyos nombres son símbolos que no son letras, como @
, también se puede hacer referencia con el uso de un signo de dólar, sin los paréntesis. Por ejemplo:
my_attr = "prefix $@ suffix"
Para escribir $
como un literal de string (es decir, para evitar la expansión de la variable), escribe $$
.
Variables predefinidas
Se puede hacer referencia a las variables "Make" predefinidas mediante cualquier atributo marcado como "Subject to 'Make variable' sustitution" en cualquier destino.
Para ver la lista de estas variables y sus valores de un conjunto determinado de opciones de compilación, ejecuta
bazel info --show_make_env [build options]
y observa las líneas superiores de salida con mayúsculas.
Consulta un ejemplo de las variables predefinidas.
Variables de opciones de la cadena de herramientas
COMPILATION_MODE
:fastbuild
,dbg
oopt
. (más detalles)
Variables de ruta de acceso
-
BINDIR
: Es la base del árbol binario generado para la arquitectura de destino.Ten en cuenta que se puede usar un árbol diferente para los programas que se ejecutan durante la compilación en la arquitectura del host, a fin de admitir la compilación cruzada.
Si deseas ejecutar una herramienta desde un
genrule
, la forma recomendada de obtener su ruta es$(execpath toolname)
, en la que toolname debe aparecer en el atributotools
degenrule
. GENDIR
: Es la base del árbol de códigos generado para la arquitectura de destino.
Variables de arquitectura de máquina
-
TARGET_CPU
: La CPU de la arquitectura de destino, p. ej.,k8
Variables predefinidas de genrule
Los siguientes están especialmente disponibles para el atributo cmd
de genrule
y, por lo general, son importantes a fin de que funcione.
Consulta un ejemplo de variables de genrule predefinidas.
OUTS
: La listaouts
degenrule
. Si solo tienes un archivo de salida, también puedes usar$@
.-
SRCS
: La listasrcs
degenrule
(o, con mayor precisión, los nombres de ruta de los archivos que corresponden a las etiquetas de la listasrcs
) Si solo tienes un archivo de origen, también puedes usar$<
. -
<
:SRCS
, si es un archivo único De lo contrario, se activa un error de compilación. -
@
:OUTS
, si es un archivo único De lo contrario, se activa un error de compilación. -
RULEDIR
: Es el directorio de salida del destino, es decir, el directorio correspondiente al nombre del paquete que contiene el destino en el árbolgenfiles
obin
. Para//my/pkg:my_genrule
, esto siempre termina enmy/pkg
, incluso si los resultados de//my/pkg:my_genrule
se encuentran en subdirectorios. -
@D
: Es el directorio de salida. Si outs tiene una entrada, se expande al directorio que contiene ese archivo. Si tiene varias entradas, se expande al directorio raíz del paquete en el árbolgenfiles
, incluso si todos los archivos de salida se encuentran en el mismo subdirectorio.Nota: Usa
RULEDIR
en lugar de@D
, ya queRULEDIR
tiene una semántica más simple y se comporta de la misma manera, independientemente de la cantidad de archivos de salida.Si la genrule necesita generar archivos intermedios temporales (quizás como resultado del uso de alguna otra herramienta, como un compilador), debe intentar escribirlos en
@D
(aunque/tmp
también se podrá escribir) y quitarlos antes de finalizar.En especial, evita escribir en directorios que contengan entradas. Pueden estar en sistemas de archivos de solo lectura. Incluso si no lo hicieras, la papelera se borraría de la papelera.
Variables predefinidas de la ruta de acceso de origen/salida
Las variables predefinidas execpath
, execpaths
, rootpath
, rootpaths
, location
y locations
toman parámetros de etiqueta (p.ej., $(execpath
//foo:bar)
) y sustituyen las rutas de acceso de archivos que indica esa etiqueta.
Para los archivos de origen, esta es la ruta de acceso relativa a tu raíz de lugar de trabajo. Para los archivos que son resultados de reglas, esta es la ruta de salida del archivo (consulta la explicación de los archivos de salida a continuación).
Consulta un ejemplo de las variables de ruta predefinidas.
-
execpath
: Denota la ruta debajo de la ejecución en la que Bazel ejecuta las acciones de compilación.En el ejemplo anterior, Bazel ejecuta todas las acciones de compilación del directorio vinculado mediante el symlink
bazel-myproject
en la raíz de tu lugar de trabajo. El archivo de origenempty.source
está vinculado en la rutabazel-myproject/testapp/empty.source
. Por lo tanto, su ruta de ejecución (que es la ruta secundaria debajo de la raíz) estestapp/empty.source
. Esta es la ruta que las acciones de compilación de compilación pueden usar para encontrar el archivo.Los archivos de salida se almacenan en etapas de manera similar, pero también se les agrega un prefijo con la subruta
bazel-out/cpu-compilation_mode/bin
(o con los resultados de las herramientas:bazel-out/cpu-opt-exec-hash/bin
). En el ejemplo anterior,//testapp:app
es una herramienta, ya que aparece en el atributotools
deshow_app_output
. Por lo tanto, su archivo de salidaapp
se escribe enbazel-myproject/bazel-out/cpu-opt-exec-hash/bin/testapp/app
. Por lo tanto, la ruta de acceso de ejecución esbazel-out/cpu-opt-exec-hash/bin/testapp/app
. Este prefijo adicional permite compilar el mismo destino, por ejemplo, para dos CPU diferentes en la misma compilación, sin que los resultados se obstruyan entre sí.La etiqueta que se pase a esta variable debe representar exactamente un archivo. Para las etiquetas que representan archivos de origen, esto se aplica de forma automática. Para las etiquetas que representan reglas, la regla debe generar solo un resultado. Si esto es falso o la etiqueta no tiene el formato correcto, la compilación fallará y mostrará un error.
-
rootpath
: Denota la ruta de acceso que un objeto binario compilado puede usar para encontrar una dependencia en el entorno de ejecución en relación con el subdirectorio de su directorio runfiles correspondiente al repositorio principal. Nota: Esto solo funciona si--enable_runfiles
está habilitado, lo que no sucede de forma predeterminada en Windows. En su lugar, usarlocationpath
para la compatibilidad multiplataforma.Esto es similar a
execpath
, pero quita los prefijos de configuración descritos con anterioridad. En el ejemplo anterior, esto significa queempty.source
yapp
usan rutas relativas de lugar de trabajo puras:testapp/empty.source
ytestapp/app
.El
rootpath
de un archivo en un repositorio externorepo
comenzará con../repo/
, seguido de la ruta relativa del repositorio.Esto tiene los mismos requisitos de “un solo resultado” que
execpath
. -
rlocationpath
: Es la ruta de acceso que un objeto binario compilado puede pasar a la funciónRlocation
de una biblioteca runfiles para encontrar una dependencia en el entorno de ejecución, ya sea en el directorio runfiles (si está disponible) o mediante el manifiesto de los archivos runfiles.Esto es similar a
rootpath
, ya que no contiene prefijos de configuración, pero difiere en que siempre comienza con el nombre del repositorio. En el ejemplo anterior, esto significa queempty.source
yapp
dan como resultado las siguientes rutas:myproject/testapp/empty.source
ymyproject/testapp/app
.El
rlocationpath
de un archivo en un repositorio externorepo
comenzará conrepo/
, seguido de la ruta relativa del repositorio.Pasar esta ruta de acceso a un objeto binario y resolverla en una ruta del sistema de archivos mediante las bibliotecas runfiles es el método preferido para encontrar dependencias durante el tiempo de ejecución. En comparación con
rootpath
, tiene la ventaja de que funciona en todas las plataformas, incluso si el directorio runfiles no está disponible.Esto tiene los mismos requisitos de “un solo resultado” que
execpath
. -
location
: Un sinónimo deexecpath
orootpath
, según el atributo que se expanda. Este es un comportamiento previo a Starlark heredado y no se recomienda, a menos que en verdad lo haga para una regla en particular. Consulta #2475 para obtener más información.
execpaths
, rootpaths
, rlocationpaths
y locations
son las variaciones en plural de execpath
, rootpath
, rlocationpaths
y location
, respectivamente. Admiten etiquetas que produzcan varias salidas, en cuyo caso cada resultado está separado por un espacio. Las reglas de salida cero y las etiquetas con formato incorrecto producen errores de compilación.
Todas las etiquetas a las que se hace referencia deben aparecer en el srcs
del destino de consumo, en los archivos de salida o en deps
. De lo contrario, la compilación fallará. Los objetivos de C++ también pueden hacer referencia a etiquetas en data
.
No es necesario que las etiquetas estén en formato canónico: foo
, :foo
y //somepkg:foo
están bien.
Variables personalizadas
Se puede hacer referencia a las variables "Make" personalizadas mediante cualquier atributo marcado como "Sujeto a sustitución de 'Make variable'", pero solo en objetivos que dependen de otros objetivos que definen estas variables.
Como práctica recomendada, todas las variables deben ser personalizadas, a menos que haya una buena razón para integrarlas a Bazel principal. Esto evita que Bazel tenga que cargar dependencias potencialmente costosas para proporcionar variables que consuman tartas.
Variables de la cadena de herramientas C++
Lo siguiente se define en las reglas de la cadena de herramientas de C++ y está disponible para cualquier regla que configure toolchains =
["@bazel_tools//tools/cpp:current_cc_toolchain"]
(o "@bazel_tools//tools/cpp:current_cc_host_toolchain"
como el equivalente de la cadena de herramientas del host). Algunas reglas, como java_binary
, incluyen de forma implícita la cadena de herramientas de C++ en la definición de la regla. Heredan estas variables de forma automática.
Las reglas de C++ integradas son mucho más sofisticadas que "ejecutar el compilador allí". Para admitir modos de compilación tan diversos como *SAN, ThinLTO, con o sin módulos, y objetos binarios optimizados cuidadosamente al mismo tiempo que las pruebas de ejecución rápida en varias plataformas, las reglas integradas hacen un gran esfuerzo para garantizar que se establezcan las entradas, las salidas y las marcas de línea de comandos correctas en cada una de las posibles acciones generadas a nivel interno.
Estas variables son un mecanismo de resguardo que pueden usar los expertos en lenguajes en casos poco frecuentes. Si te sientes tentado a usarlas, primero comunícate con los desarrolladores de Bazel.
ABI
: Es la versión de ABI de C++.-
AR
: El comando "ar" de crosstool. -
C_COMPILER
: Es el identificador del compilador C/C++, p.ej.,llvm
. -
CC
: El comando del compilador C y C++.Recomendamos usar siempre
CC_FLAGS
en combinación conCC
. No hacerlo bajo su propio riesgo. CC_FLAGS
: un conjunto mínimo de marcas para que el compilador de C/C++ pueda usar las genrules. En particular, contiene marcas para seleccionar la arquitectura correcta siCC
admite varias arquitecturas.-
NM
: El comando "nm" de crosstool. -
OBJCOPY
: Es el comando objcopy del mismo conjunto que el compilador de C/C++. -
STRIP
: El comando de eliminación del mismo paquete que el compilador de C/C++.
Variables de la cadena de herramientas de Java
Lo siguiente se define en las reglas de la cadena de herramientas de Java y está disponible para cualquier regla que configure toolchains =
["@bazel_tools//tools/jdk:current_java_runtime"]
(o "@bazel_tools//tools/jdk:current_host_java_runtime"
como el equivalente de la cadena de herramientas del host).
La mayoría de las herramientas del JDK no se deben usar directamente. Las reglas integradas de Java usan enfoques mucho más sofisticados para la compilación y el empaquetado de Java que lo que pueden expresar las herramientas ascendentes, como los JAR de la interfaz y los de JAR de la interfaz del encabezado, así como el empaquetado y la fusión de implementaciones altamente optimizadas.
Estas variables son un mecanismo de resguardo que pueden usar los expertos en lenguajes en casos poco frecuentes. Si te sientes tentado a usarlas, primero comunícate con los desarrolladores de Bazel.
-
JAVA
: El comando “java” (una máquina virtual Java). Evita esto y usa una reglajava_binary
en su lugar. Puede ser una ruta relativa. Si debes cambiar los directorios antes de invocar ajava
, debes capturar el directorio de trabajo antes de cambiarlo. JAVABASE
: El directorio base que contiene las utilidades de Java. Puede ser una ruta relativa. Tendrá un subdirectorio “bin”.
Variables definidas por Starlark
Los escritores de reglas y de la cadena de herramientas pueden definir variables completamente personalizadas si muestran un proveedor de TemplateVariableInfo. Cualquier regla que dependa de estas mediante el atributo toolchains
puede leer sus valores: