| // Copyright (C) 2016 The Android Open Source Project |
| // |
| // 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 ( |
| "fmt" |
| "strings" |
| |
| "android.googlesource.com/platform/tools/gpu/cc" |
| "android.googlesource.com/platform/tools/gpu/framework/file" |
| "android.googlesource.com/platform/tools/gpu/framework/log" |
| "android.googlesource.com/platform/tools/gpu/tools/maker/config" |
| "android.googlesource.com/platform/tools/gpu/tools/maker/do" |
| "android.googlesource.com/platform/tools/gpu/tools/maker/graph" |
| "android.googlesource.com/platform/tools/gpu/tools/maker/run" |
| ) |
| |
| func main() { run.Run() } |
| |
| const ( |
| GPURoot = "android.googlesource.com/platform/tools/gpu" |
| ) |
| |
| var ( |
| gpusrc = do.GoSrcPath(GPURoot) |
| gapidsrc = gpusrc.Join("gapid") |
| gapirpath = gpusrc.Join("cc/gapir") |
| gapiipath = gpusrc.Join("cc/gapii") |
| gapiiwinpath = gpusrc.Join("cc/gapii/windows") |
| gapiiosxpath = gpusrc.Join("cc/gapii/osx") |
| cppcoder = gpusrc.Join("cc/gapic/coder") |
| interceptorpath = gpusrc.Join("cc/third_party/prebuilts/interceptor") |
| pkginfobase = gpusrc.Join("cmd/pkginfo") |
| gfxtracerbase = gpusrc.Join("cmd/gfxtracer") |
| |
| Tools struct { |
| Apic file.Path |
| Annotate file.Path |
| CleanGenerated file.Path |
| Codergen file.Path |
| Copyright file.Path |
| Embed file.Path |
| PullAPK file.Path |
| Stringgen file.Path |
| VerifyGLESAPI file.Path |
| } |
| |
| Apps struct { |
| Gapis file.Path |
| Gapir file.Path |
| Gapit file.Path |
| } |
| |
| code = graph.Virtual("code") |
| codergen = graph.Virtual("codergen") |
| embed = graph.Virtual("embed") |
| messages = graph.Virtual("messages") |
| apic = graph.Virtual("apic") |
| annotate = graph.Virtual("annotate") |
| ccSpy = graph.Virtual("cc:spy") |
| ccGapii = graph.Virtual("cc:gapii") |
| tools = graph.Virtual("tools") |
| runtime = graph.Virtual("runtime") |
| test = graph.Virtual("test") |
| apps = graph.Virtual("apps") |
| pkginfo = graph.Virtual("pkginfo") |
| gfxtracer = graph.Virtual("gfxtracer") |
| interceptor = graph.Virtual("interceptor") |
| goTest = graph.Virtual("go_test") |
| ccTest = graph.Virtual("cc_test") |
| ) |
| |
| func init() { |
| run.Register(func(ctx log.Context) { |
| // Install rules for the build tools |
| Tools.Apic = do.GoInstall(ctx, GPURoot, "cmd/apic") |
| Tools.Annotate = do.GoInstall(ctx, GPURoot, "cmd/annotate") |
| Tools.CleanGenerated = do.GoInstall(ctx, GPURoot, "cmd/clean_generated") |
| Tools.Codergen = do.GoInstall(ctx, GPURoot, "cmd/codergen") |
| Tools.Copyright = do.GoInstall(ctx, GPURoot, "cmd/copyright") |
| Tools.Embed = do.GoInstall(ctx, GPURoot, "cmd/embed") |
| Tools.PullAPK = do.GoInstall(ctx, GPURoot, "cmd/pullapk") |
| Tools.Stringgen = do.GoInstall(ctx, GPURoot, "cmd/stringgen") |
| Tools.VerifyGLESAPI = do.GoInstall(ctx, GPURoot, "cmd/verify_gles_api") |
| graph.List(ctx, tools).DependsStruct(Tools) |
| // All the embed rules |
| embedCopyright := Embed(ctx, gpusrc.Join("tools/copyright"), "") |
| embedCodergen := Embed(ctx, gpusrc.Join("tools/codergen/template"), "") |
| embedStringgen := Embed(ctx, gpusrc.Join("cmd/stringgen"), "main") |
| graph.Creator(Tools.Apic).DependsOn(embedCopyright) |
| graph.Creator(Tools.Codergen).DependsOn(embedCopyright, embedCodergen) |
| graph.Creator(Tools.Stringgen).DependsOn(embedStringgen) |
| // The stringgen rule |
| Messages(ctx, gpusrc.Join("gapid/messages/en-us.stb.md")) |
| // All the apic rules |
| GfxApi(ctx, "test", "gfxapi_test.api") |
| GfxApi(ctx, "gles", "gles.api") |
| |
| GlApi(ctx, "gles", "gles.api") |
| VkApi(ctx, "vulkan", "vulkan.api") |
| // The codergen rule |
| Codergen(ctx, codergen, |
| "--signatures", gpusrc.Join("signatures.txt").System(), |
| "--go", |
| "-cpp", cppcoder.System(), |
| GPURoot+"/...") |
| graph.Creator(Tools.Annotate).DependsOn(codergen) |
| graph.List(ctx, code).DependsOn( |
| embed, messages, apic, codergen, annotate) |
| // The native code rules |
| cc.Graph() |
| Apps.Gapir = graph.Virtual("cc:gapir") |
| graph.Creator(ccSpy).DependsOn(code) |
| graph.Creator(ccGapii).DependsOn(code) |
| // The testing rules |
| gotest := do.GoTest(ctx, GPURoot+"/...", "integration") |
| // Runtime dependencies |
| graph.List(ctx, runtime).DependsOn(Apps.Gapir, ccSpy, ccGapii) |
| graph.Creator(gotest).DependsOn(code, runtime) |
| if config.TargetOS == config.HostOS { |
| graph.List(ctx, test).DependsOn(goTest, ccTest) |
| } else { |
| graph.List(ctx, test).DependsOn(goTest) |
| } |
| // The main binary rules |
| Apps.Gapis = do.GoInstall(ctx, GPURoot, "cmd/gapis") |
| graph.Creator(Apps.Gapis).DependsOn(code) |
| Apps.Gapit = do.GoInstall(ctx, GPURoot, "cmd/gapit") |
| graph.Creator(Apps.Gapit).DependsOn(code) |
| graph.List(ctx, apps).DependsStruct(Apps) |
| // Application launchers |
| do.Exec(Apps.Gapis).Creates(ctx, graph.Virtual("gapis")).DependsOn(Apps.Gapir) |
| // Utilties |
| do.GoRun(ctx, gpusrc.Join("cmd/clean_generated/main.go"), gpusrc).Creates(ctx, graph.Virtual("clean_gpu")) |
| do.GoRun(ctx, gpusrc.Join("cmd/copyright/main.go"), "-o", gpusrc).Creates(ctx, graph.Virtual("copyright")).DependsOn(embedCopyright) |
| // pkginfo helper APK |
| PkgInfo(ctx) |
| // Tracer Android Library AAR |
| GfxTracer(ctx) |
| // Interceptor library |
| Interceptor(ctx) |
| // The default rules |
| graph.List(ctx, graph.Default).DependsOn(tools, apps, test, interceptor) |
| }) |
| } |
| |
| func Embed(ctx log.Context, path file.Path, pkg string) file.Path { |
| out := path.Join("embed.go") |
| args := []string{"--out", out.System()} |
| if pkg != "" { |
| args = append(args, "-package", pkg) |
| } |
| files := path.Files().NotMatching("*.go", "*.gradle") |
| for _, f := range files { |
| args = append(args, f.System()) |
| } |
| s := do.Exec(Tools.Embed, args...).Creates(ctx, out) |
| for _, f := range files { |
| s.DependsOn(f) |
| } |
| graph.List(ctx, embed).DependsOn(out) |
| return out |
| } |
| |
| func Messages(ctx log.Context, files ...file.Path) file.Path { |
| out := gapidsrc.Join("messages/messages.go") |
| args := []string{ |
| "--def", out.System(), |
| "--pkg", config.Paths.Bin.Join("strings").System(), |
| } |
| for _, f := range files { |
| args = append(args, f.System()) |
| } |
| s := do.Exec(Tools.Stringgen, args...).Creates(ctx, out) |
| for _, f := range files { |
| s.DependsOn(f) |
| } |
| graph.List(ctx, messages).DependsOn(out) |
| return out |
| } |
| |
| func Annotate(ctx log.Context, dst file.Path, api file.Path) { |
| // Generate the text file for understandability. |
| snippetsText := dst.Join("snippets.text") |
| globalsSnippetsText := dst.Join("globals_snippets.text") |
| |
| snippetsBase64 := dst.Join("snippets.base64") |
| globalsSnippetsBase64 := dst.Join("globals_snippets.base64") |
| |
| snippetsEmbed := dst.Join("snippets_embed.go") |
| do.Exec(Tools.Annotate, |
| "--base64", snippetsBase64.System(), |
| "--text", snippetsText.System(), |
| "--globals_base64", globalsSnippetsBase64.System(), |
| "--globals_text", globalsSnippetsText.System(), |
| api.System()).DependsOn(api). |
| Creates(ctx, snippetsBase64, snippetsText, globalsSnippetsBase64, globalsSnippetsText) |
| // Embed the base64 file into gapis |
| do.Exec(Tools.Embed, |
| "--out", snippetsEmbed.System(), |
| snippetsBase64.System(), globalsSnippetsBase64.System()). |
| Creates(ctx, snippetsEmbed).DependsOn(snippetsBase64, globalsSnippetsBase64) |
| graph.List(ctx, annotate).DependsOn(snippetsEmbed) |
| } |
| |
| func Apic(ctx log.Context, dst file.Path, api file.Path, template file.Path) { |
| deps := config.Paths.Deps.Join(fmt.Sprintf("%v_%v.deps", api.Basename(), template.Basename())) |
| s := do.Exec(Tools.Apic, |
| "template", |
| "--dir", dst.System(), |
| "--deps", deps.System(), |
| api.System(), template.System()).DependsOn(api, template, dst, config.Paths.Deps) |
| s.UseDepsFile(ctx, deps) |
| graph.List(ctx, apic).DependsOn(deps) |
| } |
| |
| func Codergen(ctx log.Context, name file.Path, args ...string) { |
| do.Exec(Tools.Codergen, args...).Creates(ctx, name).DependsOn(apic).Access(do.GoPkgResource) |
| } |
| |
| func PkgInfo(ctx log.Context) { |
| gradleAPK := pkginfobase.Join("app/build/outputs/apk/app-debug.apk") |
| binAPK := config.Paths.Bin.Join("pkginfo.apk") |
| graph.NewStep(func(ctx log.Context, step *graph.Step) error { |
| return do.ExecAt(ctx, pkginfobase, pkginfobase.Join("gradlew"), "build") |
| }).Creates(ctx, gradleAPK) |
| do.CopyFile(ctx, binAPK, gradleAPK) |
| graph.List(ctx, pkginfo).DependsOn(binAPK) |
| } |
| |
| func GfxTracer(ctx log.Context) { |
| gradleAAR := gfxtracerbase.Join("lib/build/outputs/aar/lib-debug.aar") |
| binAAR := config.Paths.Bin.Join("gfxtracer.aar") |
| s := graph.NewStep(func(ctx log.Context, step *graph.Step) error { |
| return do.ExecAt(ctx, gfxtracerbase, gfxtracerbase.Join("gradlew"), "build") |
| }).Creates(ctx, gradleAAR) |
| |
| jniLibs := gfxtracerbase.Join("lib/src/main/jniLibs") |
| do.CopyFile(ctx, jniLibs.Join("armeabi-v7a/libgapii.so"), config.Paths.Bin.Join("android-armv7a/libgapii.so")) |
| s.DependsOn(jniLibs.Join("armeabi-v7a/libgapii.so")) |
| do.CopyFile(ctx, jniLibs.Join("arm64-v8a/libgapii.so"), config.Paths.Bin.Join("android-armv8a/libgapii.so")) |
| s.DependsOn(jniLibs.Join("/arm64-v8a/libgapii.so")) |
| |
| do.CopyFile(ctx, binAAR, gradleAAR) |
| graph.List(ctx, gfxtracer).DependsOn(binAAR) |
| } |
| |
| // Interceptor copies the prebuilt files in interceptorpath to the bin directory |
| // as the virtual list 'interceptor'. |
| func Interceptor(ctx log.Context) { |
| graph.List(ctx, interceptor) |
| for _, file := range interceptorpath.Glob("*/*") { |
| rel, _ := file.RelativeTo(interceptorpath) |
| dst := config.Paths.Bin.Join(rel) |
| do.CopyFile(ctx, dst, file) |
| graph.List(ctx, interceptor).DependsOn(dst) |
| } |
| } |
| |
| func VkApi(ctx log.Context, pkg string, api string) { |
| out := gapidsrc.Join("gfxapi", pkg) |
| in := out.Join(api) |
| templates := gapidsrc.Join("gfxapi", "vulkan", "templates") |
| root_templates := gapidsrc.Join("gfxapi", "templates") |
| // gapiiv code |
| istest := strings.HasSuffix(pkg, "test") |
| Apic(ctx, out, in, gapidsrc.Join("gfxapi", "templates", "api.go.tmpl")) |
| Apic(ctx, out, in, gapidsrc.Join("gfxapi", "templates", "mutate.go.tmpl")) |
| Annotate(ctx, out, in) |
| |
| if istest { |
| return |
| } |
| |
| Apic(ctx, gapiipath, in, templates.Join("api_spy.cpp.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("api_exports.cpp.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("api_imports.cpp.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("api_imports.h.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("vk_spy_helpers.cpp.tmpl")) |
| Apic(ctx, gapiipath, in, root_templates.Join("api_spy.h.tmpl")) |
| Apic(ctx, gapiipath, in, root_templates.Join("api_types.h.tmpl")) |
| } |
| |
| func GlApi(ctx log.Context, pkg string, api string) { |
| out := gapidsrc.Join("gfxapi", pkg) |
| in := out.Join(api) |
| templates := gapidsrc.Join("gfxapi", "gles", "templates") |
| istest := strings.HasSuffix(pkg, "test") |
| if istest { |
| return |
| } |
| |
| Apic(ctx, gapiipath, in, templates.Join("api_spy.cpp.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("api_exports.cpp.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("api_imports.cpp.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("api_imports.h.tmpl")) |
| } |
| |
| func GfxApi(ctx log.Context, pkg string, api string) { |
| out := gapidsrc.Join("gfxapi", pkg) |
| in := out.Join(api) |
| templates := gapidsrc.Join("gfxapi", "templates") |
| istest := strings.HasSuffix(pkg, "test") |
| // go code |
| Apic(ctx, out, in, templates.Join("api.go.tmpl")) |
| Apic(ctx, out, in, templates.Join("mutate.go.tmpl")) |
| Annotate(ctx, out, in) |
| if istest { |
| return |
| } |
| // gapir code |
| Apic(ctx, gapirpath, in, templates.Join("gfx_api.cpp.tmpl")) |
| Apic(ctx, gapirpath, in, templates.Join("gfx_api.h.tmpl")) |
| // gapii code |
| Apic(ctx, gapiipath, in, templates.Join("api_spy.h.tmpl")) |
| Apic(ctx, gapiipath, in, templates.Join("api_types.h.tmpl")) |
| Apic(ctx, gapiiwinpath, in, templates.Join("opengl32_exports.def.tmpl")) |
| Apic(ctx, gapiiwinpath, in, templates.Join("opengl32_resolve.cpp.tmpl")) |
| Apic(ctx, gapiiwinpath, in, templates.Join("opengl32_x64.asm.tmpl")) |
| Apic(ctx, gapiiosxpath, in, templates.Join("opengl_framework_exports.cpp.tmpl")) |
| } |