bloaty: measure stripped Rust binaries
Modify bloaty's MeasureSizeForPath to allow a module to provide multiple paths. This is used to measure both unstripped and stripped libraries/binaries. Add unit test to ensure correct measurements are generated for Rust. Test: m out/soong/binary_sizes.pb.gz Change-Id: I59439b77dbf1cf5ad71e1c02996a6a90938536b4
This commit is contained in:
parent
4fab05a2ad
commit
e4dd14b25f
7 changed files with 76 additions and 19 deletions
|
@ -11,6 +11,7 @@ bootstrap_go_package {
|
|||
],
|
||||
srcs: [
|
||||
"bloaty.go",
|
||||
"testing.go",
|
||||
],
|
||||
pluginFor: ["soong_build"],
|
||||
}
|
||||
|
|
|
@ -52,12 +52,28 @@ func init() {
|
|||
pctx.SourcePathVariable("bloaty", "prebuilts/build-tools/${hostPrebuiltTag}/bin/bloaty")
|
||||
pctx.HostBinToolVariable("bloatyMerger", "bloaty_merger")
|
||||
android.RegisterSingletonType("file_metrics", fileSizesSingleton)
|
||||
fileSizeMeasurerKey = blueprint.NewProvider(android.ModuleOutPath{})
|
||||
fileSizeMeasurerKey = blueprint.NewProvider(measuredFiles{})
|
||||
}
|
||||
|
||||
// MeasureSizeForPath should be called by binary producers (e.g. in builder.go).
|
||||
func MeasureSizeForPath(ctx android.ModuleContext, filePath android.WritablePath) {
|
||||
ctx.SetProvider(fileSizeMeasurerKey, filePath)
|
||||
// measuredFiles contains the paths of the files measured by a module.
|
||||
type measuredFiles struct {
|
||||
paths []android.WritablePath
|
||||
}
|
||||
|
||||
// MeasureSizeForPaths should be called by binary producers to measure the
|
||||
// sizes of artifacts. It must only be called once per module; it will panic
|
||||
// otherwise.
|
||||
func MeasureSizeForPaths(ctx android.ModuleContext, paths ...android.OptionalPath) {
|
||||
mf := measuredFiles{}
|
||||
for _, p := range paths {
|
||||
if !p.Valid() {
|
||||
continue
|
||||
}
|
||||
if p, ok := p.Path().(android.WritablePath); ok {
|
||||
mf.paths = append(mf.paths, p)
|
||||
}
|
||||
}
|
||||
ctx.SetProvider(fileSizeMeasurerKey, mf)
|
||||
}
|
||||
|
||||
type sizesSingleton struct{}
|
||||
|
@ -68,21 +84,22 @@ func fileSizesSingleton() android.Singleton {
|
|||
|
||||
func (singleton *sizesSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
||||
var deps android.Paths
|
||||
// Visit all modules. If the size provider give us a binary path to measure,
|
||||
// create the rule to measure it.
|
||||
ctx.VisitAllModules(func(m android.Module) {
|
||||
if !ctx.ModuleHasProvider(m, fileSizeMeasurerKey) {
|
||||
return
|
||||
}
|
||||
filePath := ctx.ModuleProvider(m, fileSizeMeasurerKey).(android.ModuleOutPath)
|
||||
sizeFile := filePath.InSameDir(ctx, filePath.Base()+bloatyDescriptorExt)
|
||||
ctx.Build(pctx, android.BuildParams{
|
||||
Rule: bloaty,
|
||||
Description: "bloaty " + filePath.Rel(),
|
||||
Input: filePath,
|
||||
Output: sizeFile,
|
||||
})
|
||||
deps = append(deps, sizeFile)
|
||||
filePaths := ctx.ModuleProvider(m, fileSizeMeasurerKey).(measuredFiles)
|
||||
for _, path := range filePaths.paths {
|
||||
filePath := path.(android.ModuleOutPath)
|
||||
sizeFile := filePath.InSameDir(ctx, filePath.Base()+bloatyDescriptorExt)
|
||||
ctx.Build(pctx, android.BuildParams{
|
||||
Rule: bloaty,
|
||||
Description: "bloaty " + filePath.Rel(),
|
||||
Input: filePath,
|
||||
Output: sizeFile,
|
||||
})
|
||||
deps = append(deps, sizeFile)
|
||||
}
|
||||
})
|
||||
|
||||
ctx.Build(pctx, android.BuildParams{
|
||||
|
|
25
bloaty/testing.go
Normal file
25
bloaty/testing.go
Normal file
|
@ -0,0 +1,25 @@
|
|||
// Copyright 2021 Google Inc. 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 bloaty
|
||||
|
||||
import (
|
||||
"android/soong/android"
|
||||
)
|
||||
|
||||
// Preparer that will define the default bloaty singleton.
|
||||
var PrepareForTestWithBloatyDefaultModules = android.GroupFixturePreparers(
|
||||
android.FixtureRegisterWithContext(func(ctx android.RegistrationContext) {
|
||||
ctx.RegisterSingletonType("file_metrics", fileSizesSingleton)
|
||||
}))
|
|
@ -21,7 +21,6 @@ import (
|
|||
"github.com/google/blueprint"
|
||||
|
||||
"android/soong/android"
|
||||
"android/soong/bloaty"
|
||||
"android/soong/rust/config"
|
||||
)
|
||||
|
||||
|
@ -254,8 +253,6 @@ func transformSrctoCrate(ctx ModuleContext, main android.Path, deps PathDeps, fl
|
|||
implicits = append(implicits, clippyFile)
|
||||
}
|
||||
|
||||
bloaty.MeasureSizeForPath(ctx, outputFile)
|
||||
|
||||
ctx.Build(pctx, android.BuildParams{
|
||||
Rule: rustc,
|
||||
Description: "rustc " + main.Rel(),
|
||||
|
|
|
@ -22,6 +22,7 @@ import (
|
|||
"github.com/google/blueprint/proptools"
|
||||
|
||||
"android/soong/android"
|
||||
"android/soong/bloaty"
|
||||
"android/soong/cc"
|
||||
cc_config "android/soong/cc/config"
|
||||
"android/soong/rust/config"
|
||||
|
@ -731,8 +732,8 @@ func (mod *Module) GenerateAndroidBuildActions(actx android.ModuleContext) {
|
|||
if mod.compiler != nil && !mod.compiler.Disabled() {
|
||||
mod.compiler.initialize(ctx)
|
||||
unstrippedOutputFile := mod.compiler.compile(ctx, flags, deps)
|
||||
|
||||
mod.unstrippedOutputFile = android.OptionalPathForPath(unstrippedOutputFile)
|
||||
bloaty.MeasureSizeForPaths(ctx, mod.compiler.strippedOutputFilePath(), mod.unstrippedOutputFile)
|
||||
|
||||
apexInfo := actx.Provider(android.ApexInfoProvider).(android.ApexInfo)
|
||||
if mod.installable(apexInfo) {
|
||||
|
|
|
@ -384,3 +384,17 @@ func TestMultilib(t *testing.T) {
|
|||
_ = ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_rlib_dylib-std")
|
||||
_ = ctx.ModuleForTests("libfoo", "android_arm_armv7-a-neon_rlib_dylib-std")
|
||||
}
|
||||
|
||||
// Test that library size measurements are generated.
|
||||
func TestLibrarySizes(t *testing.T) {
|
||||
ctx := testRust(t, `
|
||||
rust_library_dylib {
|
||||
name: "libwaldo",
|
||||
srcs: ["foo.rs"],
|
||||
crate_name: "waldo",
|
||||
}`)
|
||||
|
||||
m := ctx.SingletonForTests("file_metrics")
|
||||
m.Output("libwaldo.dylib.so.bloaty.csv")
|
||||
m.Output("stripped/libwaldo.dylib.so.bloaty.csv")
|
||||
}
|
||||
|
|
|
@ -16,6 +16,7 @@ package rust
|
|||
|
||||
import (
|
||||
"android/soong/android"
|
||||
"android/soong/bloaty"
|
||||
"android/soong/cc"
|
||||
)
|
||||
|
||||
|
@ -34,6 +35,7 @@ const rustDefaultsDir = "defaults/rust/"
|
|||
// Preparer that will define default rust modules, e.g. standard prebuilt modules.
|
||||
var PrepareForTestWithRustDefaultModules = android.GroupFixturePreparers(
|
||||
cc.PrepareForTestWithCcDefaultModules,
|
||||
bloaty.PrepareForTestWithBloatyDefaultModules,
|
||||
PrepareForTestWithRustBuildComponents,
|
||||
android.FixtureAddTextFile(rustDefaultsDir+"Android.bp", GatherRequiredDepsForTest()),
|
||||
)
|
||||
|
|
Loading…
Reference in a new issue