diff options
-rw-r--r-- | Android.bp | 1 | ||||
-rw-r--r-- | android/config.go | 16 | ||||
-rw-r--r-- | android/writedocs.go | 73 | ||||
-rw-r--r-- | cmd/soong_build/Android.bp | 1 | ||||
-rw-r--r-- | cmd/soong_build/main.go | 16 | ||||
-rw-r--r-- | cmd/soong_build/writedocs.go | 129 |
6 files changed, 234 insertions, 2 deletions
@@ -61,6 +61,7 @@ bootstrap_go_package { "android/testing.go", "android/util.go", "android/variable.go", + "android/writedocs.go", // Lock down environment access last "android/env.go", diff --git a/android/config.go b/android/config.go index 0eebb5fb..16870f10 100644 --- a/android/config.go +++ b/android/config.go @@ -25,6 +25,7 @@ import ( "strings" "sync" + "github.com/google/blueprint/bootstrap" "github.com/google/blueprint/proptools" ) @@ -67,6 +68,7 @@ type config struct { FileConfigurableOptions ProductVariables productVariables + PrimaryBuilder string ConfigFileName string ProductVariablesFileName string @@ -91,6 +93,8 @@ type config struct { useOpenJDK9 bool // Use OpenJDK9, but possibly target 1.8 targetOpenJDK9 bool // Use OpenJDK9 and target 1.9 + stopBefore bootstrap.StopBefore + OncePer } @@ -312,14 +316,22 @@ func (c *config) fromEnv() error { return nil } -func (c *config) RemoveAbandonedFiles() bool { - return false +func (c *config) StopBefore() bootstrap.StopBefore { + return c.stopBefore +} + +func (c *config) SetStopBefore(stopBefore bootstrap.StopBefore) { + c.stopBefore = stopBefore } +var _ bootstrap.ConfigStopBefore = (*config)(nil) + func (c *config) BlueprintToolLocation() string { return filepath.Join(c.buildDir, "host", c.PrebuiltOS(), "bin") } +var _ bootstrap.ConfigBlueprintToolLocation = (*config)(nil) + // HostSystemTool looks for non-hermetic tools from the system we're running on. // Generally shouldn't be used, but useful to find the XCode SDK, etc. func (c *config) HostSystemTool(name string) string { diff --git a/android/writedocs.go b/android/writedocs.go new file mode 100644 index 00000000..9737030e --- /dev/null +++ b/android/writedocs.go @@ -0,0 +1,73 @@ +// Copyright 2015 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 android + +import ( + "fmt" + "os" + "path/filepath" + "strings" + + "github.com/google/blueprint" +) + +func init() { + RegisterSingletonType("writedocs", DocsSingleton) +} + +func DocsSingleton() Singleton { + return &docsSingleton{} +} + +type docsSingleton struct{} + +func primaryBuilderPath(ctx SingletonContext) Path { + primaryBuilder, err := filepath.Rel(ctx.Config().BuildDir(), os.Args[0]) + if err != nil { + ctx.Errorf("path to primary builder %q is not in build dir %q", + os.Args[0], ctx.Config().BuildDir()) + } + + return PathForOutput(ctx, primaryBuilder) +} + +func (c *docsSingleton) GenerateBuildActions(ctx SingletonContext) { + // Generate build system docs for the primary builder. Generating docs reads the source + // files used to build the primary builder, but that dependency will be picked up through + // the dependency on the primary builder itself. There are no dependencies on the + // Blueprints files, as any relevant changes to the Blueprints files would have caused + // a rebuild of the primary builder. + docsFile := PathForOutput(ctx, "docs", "soong_build.html") + primaryBuilder := primaryBuilderPath(ctx) + soongDocs := ctx.Rule(pctx, "soongDocs", + blueprint.RuleParams{ + Command: fmt.Sprintf("%s --soong_docs %s %s", + primaryBuilder.String(), docsFile.String(), strings.Join(os.Args[1:], " ")), + CommandDeps: []string{primaryBuilder.String()}, + Description: fmt.Sprintf("%s docs $out", primaryBuilder.Base()), + }) + + ctx.Build(pctx, BuildParams{ + Rule: soongDocs, + Output: docsFile, + }) + + // Add a phony target for building the documentation + ctx.Build(pctx, BuildParams{ + Rule: blueprint.Phony, + Output: PathForPhony(ctx, "soong_docs"), + Input: docsFile, + }) +} diff --git a/cmd/soong_build/Android.bp b/cmd/soong_build/Android.bp index d9daafc4..2536a535 100644 --- a/cmd/soong_build/Android.bp +++ b/cmd/soong_build/Android.bp @@ -23,6 +23,7 @@ bootstrap_go_binary { ], srcs: [ "main.go", + "writedocs.go", ], primaryBuilder: true, } diff --git a/cmd/soong_build/main.go b/cmd/soong_build/main.go index ddde1c59..40beab8c 100644 --- a/cmd/soong_build/main.go +++ b/cmd/soong_build/main.go @@ -25,6 +25,14 @@ import ( "android/soong/android" ) +var ( + docFile string +) + +func init() { + flag.StringVar(&docFile, "soong_docs", "", "build documentation file to output") +} + func newNameResolver(config android.Config) *android.NameResolver { namespacePathsToExport := make(map[string]bool) @@ -56,9 +64,17 @@ func main() { os.Exit(1) } + if docFile != "" { + configuration.SetStopBefore(bootstrap.StopBeforePrepareBuildActions) + } + ctx.SetNameInterface(newNameResolver(configuration)) ctx.SetAllowMissingDependencies(configuration.AllowMissingDependencies()) bootstrap.Main(ctx.Context, configuration, configuration.ConfigFileName, configuration.ProductVariablesFileName) + + if docFile != "" { + writeDocs(ctx, docFile) + } } diff --git a/cmd/soong_build/writedocs.go b/cmd/soong_build/writedocs.go new file mode 100644 index 00000000..a6686c0d --- /dev/null +++ b/cmd/soong_build/writedocs.go @@ -0,0 +1,129 @@ +// Copyright 2017 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 main + +import ( + "android/soong/android" + "bytes" + "html/template" + "io/ioutil" + + "github.com/google/blueprint/bootstrap" +) + +func writeDocs(ctx *android.Context, filename string) error { + moduleTypeList, err := bootstrap.ModuleTypeDocs(ctx.Context) + if err != nil { + return err + } + + buf := &bytes.Buffer{} + + unique := 0 + + tmpl, err := template.New("file").Funcs(map[string]interface{}{ + "unique": func() int { + unique++ + return unique + }}).Parse(fileTemplate) + if err != nil { + return err + } + + err = tmpl.Execute(buf, moduleTypeList) + if err != nil { + return err + } + + err = ioutil.WriteFile(filename, buf.Bytes(), 0666) + if err != nil { + return err + } + + return nil +} + +const ( + fileTemplate = ` +<html> +<head> +<title>Build Docs</title> +<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css"> +<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script> +<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/js/bootstrap.min.js"></script> +</head> +<body> +<h1>Build Docs</h1> +<div class="panel-group" id="accordion" role="tablist" aria-multiselectable="true"> + {{range .}} + {{ $collapseIndex := unique }} + <div class="panel panel-default"> + <div class="panel-heading" role="tab" id="heading{{$collapseIndex}}"> + <h2 class="panel-title"> + <a class="collapsed" role="button" data-toggle="collapse" data-parent="#accordion" href="#collapse{{$collapseIndex}}" aria-expanded="false" aria-controls="collapse{{$collapseIndex}}"> + {{.Name}} + </a> + </h2> + </div> + </div> + <div id="collapse{{$collapseIndex}}" class="panel-collapse collapse" role="tabpanel" aria-labelledby="heading{{$collapseIndex}}"> + <div class="panel-body"> + <p>{{.Text}}</p> + {{range .PropertyStructs}} + <p>{{.Text}}</p> + {{template "properties" .Properties}} + {{end}} + </div> + </div> + {{end}} +</div> +</body> +</html> + +{{define "properties"}} + <div class="panel-group" id="accordion" role="tablist" aria-multiselectable="true"> + {{range .}} + {{$collapseIndex := unique}} + {{if .Properties}} + <div class="panel panel-default"> + <div class="panel-heading" role="tab" id="heading{{$collapseIndex}}"> + <h4 class="panel-title"> + <a class="collapsed" role="button" data-toggle="collapse" data-parent="#accordion" href="#collapse{{$collapseIndex}}" aria-expanded="false" aria-controls="collapse{{$collapseIndex}}"> + {{.Name}}{{range .OtherNames}}, {{.}}{{end}} + </a> + </h4> + </div> + </div> + <div id="collapse{{$collapseIndex}}" class="panel-collapse collapse" role="tabpanel" aria-labelledby="heading{{$collapseIndex}}"> + <div class="panel-body"> + <p>{{.Text}}</p> + {{range .OtherTexts}}<p>{{.}}</p>{{end}} + {{template "properties" .Properties}} + </div> + </div> + {{else}} + <div> + <h4>{{.Name}}{{range .OtherNames}}, {{.}}{{end}}</h4> + <p>{{.Text}}</p> + {{range .OtherTexts}}<p>{{.}}</p>{{end}} + <p><i>Type: {{.Type}}</i></p> + {{if .Default}}<p><i>Default: {{.Default}}</i></p>{{end}} + </div> + {{end}} + {{end}} + </div> +{{end}} +` +) |