// Copyright 2014 The Bazel Authors. All rights reserved. // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. package com.google.devtools.build.lib.rules.java; import static com.google.common.base.Preconditions.checkArgument; import com.google.common.base.Optional; import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableMap; import com.google.devtools.build.lib.analysis.config.BuildConfiguration.Fragment; import com.google.devtools.build.lib.analysis.config.BuildConfiguration.StrictDepsMode; import com.google.devtools.build.lib.analysis.config.BuildOptions; import com.google.devtools.build.lib.analysis.config.InvalidConfigurationException; import com.google.devtools.build.lib.analysis.skylark.annotations.SkylarkConfigurationField; import com.google.devtools.build.lib.cmdline.Label; import com.google.devtools.build.lib.cmdline.LabelSyntaxException; import com.google.devtools.build.lib.concurrent.ThreadSafety.Immutable; import com.google.devtools.build.lib.events.Event; import com.google.devtools.build.lib.events.EventHandler; import com.google.devtools.build.lib.skyframe.serialization.autocodec.AutoCodec; import com.google.devtools.build.lib.skylarkbuildapi.java.JavaConfigurationApi; import com.google.devtools.common.options.TriState; import java.util.List; import java.util.Map; import javax.annotation.Nullable; /** A java compiler configuration containing the flags required for compilation. */ @AutoCodec @Immutable public final class JavaConfiguration extends Fragment implements JavaConfigurationApi { /** Values for the --java_classpath option */ public enum JavaClasspathMode { /** Use full transitive classpaths, the default behavior. */ OFF, /** JavaBuilder computes the reduced classpath before invoking javac. */ JAVABUILDER, } /** Values for the --experimental_one_version_enforcement option */ public enum OneVersionEnforcementLevel { /** Don't attempt to check for one version violations (the default) */ OFF, /** * Check for one version violations, emit warnings to stderr if any are found, but don't break * the binary. */ WARNING, /** * Check for one version violations, emit warnings to stderr if any are found, and break the * rule if it's found. */ ERROR } /** Values for the --experimental_import_deps_checking option */ public enum ImportDepsCheckingLevel { /** Turn off the import_deps checking. */ OFF, /** Emit warnings when the dependencies of java_import/aar_import are not complete. */ WARNING, /** Emit errors when the dependencies of java_import/aar_import are not complete. */ ERROR } /** * Values for the --java_optimization_mode option, which controls how Proguard is run over binary * and test targets. Note that for the moment this has no effect when building library targets. */ public enum JavaOptimizationMode { /** Proguard is used iff top-level target has {@code proguard_specs} attribute. */ LEGACY, /** * No link-time optimizations are applied, regardless of the top-level target's attributes. In * practice this mode skips Proguard completely, rather than invoking Proguard as a no-op. */ NOOP("-dontshrink", "-dontoptimize", "-dontobfuscate"), /** * Symbols have different names except where configured not to rename. This mode is primarily * intended to aid in identifying missing configuration directives that prevent symbols accessed * reflectively etc. from being renamed or removed. */ RENAME("-dontshrink", "-dontoptimize"), /** * "Quickly" produce small binary typically without changing code structure. In practice this * mode removes unreachable code and uses short symbol names except where configured not to * rename or remove. This mode should build faster than {@link #OPTIMIZE_MINIFY} and may hence * be preferable during development. */ FAST_MINIFY("-dontoptimize"), /** * Produce fully optimized binary with short symbol names and unreachable code removed. Unlike * {@link #FAST_MINIFY}, this mode may apply code transformations, in addition to removing and * renaming code as the configuration allows, to produce a more compact binary. This mode * should be preferable for producing and testing release binaries. */ OPTIMIZE_MINIFY; private final String proguardDirectives; JavaOptimizationMode(String... donts) { StringBuilder proguardDirectives = new StringBuilder(); for (String dont : donts) { checkArgument(dont.startsWith("-dont"), "invalid Proguard directive: %s", dont); proguardDirectives.append(dont).append('\n'); } this.proguardDirectives = proguardDirectives.toString(); } /** * Returns additional Proguard directives necessary for this mode (can be empty). */ public String getImplicitProguardDirectives() { return proguardDirectives; } /** * Returns true if all affected targets should produce mappings from original to renamed symbol * names, regardless of the proguard_generate_mapping attribute. This should be the case for * all modes that force symbols to be renamed. By contrast, the {@link #NOOP} mode will never * produce a mapping file since no symbols are ever renamed. */ public boolean alwaysGenerateOutputMapping() { switch (this) { case LEGACY: case NOOP: return false; case RENAME: case FAST_MINIFY: case OPTIMIZE_MINIFY: return true; default: throw new AssertionError("Unexpected mode: " + this); } } } private final ImmutableList commandLineJavacFlags; private final Label javaLauncherLabel; private final boolean useIjars; private final boolean useHeaderCompilation; private final boolean headerCompilationDisableJavacFallback; private final boolean generateJavaDeps; private final boolean strictDepsJavaProtos; private final boolean protoGeneratedStrictDeps; private final OneVersionEnforcementLevel enforceOneVersion; private final boolean enforceOneVersionOnJavaTests; private final ImportDepsCheckingLevel importDepsCheckingLevel; private final boolean allowRuntimeDepsOnNeverLink; private final JavaClasspathMode javaClasspath; private final ImmutableList defaultJvmFlags; private final ImmutableList checkedConstraints; private final StrictDepsMode strictJavaDeps; private final String fixDepsTool; private final Label proguardBinary; private final ImmutableList