diff --git a/android/config.go b/android/config.go index 350893ba5..b6ef26848 100644 --- a/android/config.go +++ b/android/config.go @@ -406,6 +406,14 @@ func NewConfig(srcDir, buildDir string) (Config, error) { return Config{}, err } + if Bool(config.productVariables.GcovCoverage) && Bool(config.productVariables.ClangCoverage) { + return Config{}, fmt.Errorf("GcovCoverage and ClangCoverage cannot both be set") + } + + config.productVariables.Native_coverage = proptools.BoolPtr( + Bool(config.productVariables.GcovCoverage) || + Bool(config.productVariables.ClangCoverage)) + return Config{config}, nil } @@ -1037,27 +1045,55 @@ func (c *deviceConfig) SamplingPGO() bool { return Bool(c.config.productVariables.SamplingPGO) } -func (c *config) NativeLineCoverage() bool { - return Bool(c.productVariables.NativeLineCoverage) +// JavaCoverageEnabledForPath returns whether Java code coverage is enabled for +// path. Coverage is enabled by default when the product variable +// JavaCoveragePaths is empty. If JavaCoveragePaths is not empty, coverage is +// enabled for any path which is part of this variable (and not part of the +// JavaCoverageExcludePaths product variable). Value "*" in JavaCoveragePaths +// represents any path. +func (c *deviceConfig) JavaCoverageEnabledForPath(path string) bool { + coverage := false + if c.config.productVariables.JavaCoveragePaths == nil || + InList("*", c.config.productVariables.JavaCoveragePaths) || + HasAnyPrefix(path, c.config.productVariables.JavaCoveragePaths) { + coverage = true + } + if coverage && c.config.productVariables.JavaCoverageExcludePaths != nil { + if HasAnyPrefix(path, c.config.productVariables.JavaCoverageExcludePaths) { + coverage = false + } + } + return coverage } +// Returns true if gcov or clang coverage is enabled. func (c *deviceConfig) NativeCoverageEnabled() bool { - return Bool(c.config.productVariables.Native_coverage) || Bool(c.config.productVariables.NativeLineCoverage) + return Bool(c.config.productVariables.GcovCoverage) || + Bool(c.config.productVariables.ClangCoverage) } func (c *deviceConfig) ClangCoverageEnabled() bool { return Bool(c.config.productVariables.ClangCoverage) } -func (c *deviceConfig) CoverageEnabledForPath(path string) bool { +func (c *deviceConfig) GcovCoverageEnabled() bool { + return Bool(c.config.productVariables.GcovCoverage) +} + +// NativeCoverageEnabledForPath returns whether (GCOV- or Clang-based) native +// code coverage is enabled for path. By default, coverage is not enabled for a +// given path unless it is part of the NativeCoveragePaths product variable (and +// not part of the NativeCoverageExcludePaths product variable). Value "*" in +// NativeCoveragePaths represents any path. +func (c *deviceConfig) NativeCoverageEnabledForPath(path string) bool { coverage := false - if c.config.productVariables.CoveragePaths != nil { - if InList("*", c.config.productVariables.CoveragePaths) || HasAnyPrefix(path, c.config.productVariables.CoveragePaths) { + if c.config.productVariables.NativeCoveragePaths != nil { + if InList("*", c.config.productVariables.NativeCoveragePaths) || HasAnyPrefix(path, c.config.productVariables.NativeCoveragePaths) { coverage = true } } - if coverage && c.config.productVariables.CoverageExcludePaths != nil { - if HasAnyPrefix(path, c.config.productVariables.CoverageExcludePaths) { + if coverage && c.config.productVariables.NativeCoverageExcludePaths != nil { + if HasAnyPrefix(path, c.config.productVariables.NativeCoverageExcludePaths) { coverage = false } } diff --git a/android/variable.go b/android/variable.go index 4da33259c..983c23567 100644 --- a/android/variable.go +++ b/android/variable.go @@ -253,11 +253,16 @@ type productVariables struct { SamplingPGO *bool `json:",omitempty"` - NativeLineCoverage *bool `json:",omitempty"` - Native_coverage *bool `json:",omitempty"` - ClangCoverage *bool `json:",omitempty"` - CoveragePaths []string `json:",omitempty"` - CoverageExcludePaths []string `json:",omitempty"` + JavaCoveragePaths []string `json:",omitempty"` + JavaCoverageExcludePaths []string `json:",omitempty"` + + GcovCoverage *bool `json:",omitempty"` + ClangCoverage *bool `json:",omitempty"` + NativeCoveragePaths []string `json:",omitempty"` + NativeCoverageExcludePaths []string `json:",omitempty"` + + // Set by NewConfig + Native_coverage *bool DevicePrefer32BitApps *bool `json:",omitempty"` DevicePrefer32BitExecutables *bool `json:",omitempty"` diff --git a/apex/apex.go b/apex/apex.go index a63a8d60c..f9c9b87f3 100644 --- a/apex/apex.go +++ b/apex/apex.go @@ -1660,7 +1660,7 @@ func (a *apexBundle) IsSanitizerEnabled(ctx android.BaseModuleContext, sanitizer } func (a *apexBundle) IsNativeCoverageNeeded(ctx android.BaseModuleContext) bool { - return ctx.Device() && (ctx.DeviceConfig().NativeCoverageEnabled() || ctx.DeviceConfig().ClangCoverageEnabled()) + return ctx.Device() && ctx.DeviceConfig().NativeCoverageEnabled() } func (a *apexBundle) PreventInstall() { diff --git a/apex/vndk_test.go b/apex/vndk_test.go index 523ac2630..8557faee1 100644 --- a/apex/vndk_test.go +++ b/apex/vndk_test.go @@ -155,6 +155,7 @@ func TestVndkApexUsesVendorVariant(t *testing.T) { sdk_version: "current", } `, func(fs map[string][]byte, config android.Config) { + config.TestProductVariables.GcovCoverage = proptools.BoolPtr(true) config.TestProductVariables.Native_coverage = proptools.BoolPtr(true) }) diff --git a/cc/coverage.go b/cc/coverage.go index bde07fd63..4431757d5 100644 --- a/cc/coverage.go +++ b/cc/coverage.go @@ -74,8 +74,8 @@ func (cov *coverage) deps(ctx DepsContext, deps Deps) Deps { } func (cov *coverage) flags(ctx ModuleContext, flags Flags, deps PathDeps) (Flags, PathDeps) { - gcovCoverage := ctx.DeviceConfig().NativeCoverageEnabled() clangCoverage := ctx.DeviceConfig().ClangCoverageEnabled() + gcovCoverage := ctx.DeviceConfig().GcovCoverageEnabled() if !gcovCoverage && !clangCoverage { return flags, deps @@ -151,7 +151,7 @@ func (cov *coverage) flags(ctx ModuleContext, flags Flags, deps PathDeps) (Flags func (cov *coverage) begin(ctx BaseModuleContext) { // Coverage is disabled globally - if !ctx.DeviceConfig().NativeCoverageEnabled() && !ctx.DeviceConfig().ClangCoverageEnabled() { + if !ctx.DeviceConfig().NativeCoverageEnabled() { return } @@ -175,7 +175,7 @@ func (cov *coverage) begin(ctx BaseModuleContext) { if needCoverageVariant { // Coverage variant is actually built with coverage if enabled for its module path - needCoverageBuild = ctx.DeviceConfig().CoverageEnabledForPath(ctx.ModuleDir()) + needCoverageBuild = ctx.DeviceConfig().NativeCoverageEnabledForPath(ctx.ModuleDir()) } } diff --git a/java/app.go b/java/app.go index 3f12e91c0..a0b208f75 100755 --- a/java/app.go +++ b/java/app.go @@ -952,7 +952,7 @@ func (a *AndroidApp) Privileged() bool { } func (a *AndroidApp) IsNativeCoverageNeeded(ctx android.BaseModuleContext) bool { - return ctx.Device() && (ctx.DeviceConfig().NativeCoverageEnabled() || ctx.DeviceConfig().ClangCoverageEnabled()) + return ctx.Device() && ctx.DeviceConfig().NativeCoverageEnabled() } func (a *AndroidApp) PreventInstall() { diff --git a/java/java.go b/java/java.go index 5632ff586..72c91a5e0 100644 --- a/java/java.go +++ b/java/java.go @@ -633,7 +633,9 @@ type jniLib struct { } func (j *Module) shouldInstrument(ctx android.BaseModuleContext) bool { - return j.properties.Instrument && ctx.Config().IsEnvTrue("EMMA_INSTRUMENT") + return j.properties.Instrument && + ctx.Config().IsEnvTrue("EMMA_INSTRUMENT") && + ctx.DeviceConfig().JavaCoverageEnabledForPath(ctx.ModuleDir()) } func (j *Module) shouldInstrumentStatic(ctx android.BaseModuleContext) bool {