165 lines
5.3 KiB
Go
165 lines
5.3 KiB
Go
|
// Copyright (C) 2019 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 bionic
|
||
|
|
||
|
import (
|
||
|
"fmt"
|
||
|
"io"
|
||
|
"strings"
|
||
|
|
||
|
"github.com/google/blueprint/proptools"
|
||
|
|
||
|
"android/soong/android"
|
||
|
)
|
||
|
|
||
|
// bionic_mountpoint is a module type that is specialized to create
|
||
|
// mount points for Bionic files (libc, libdl, libm, and linker).
|
||
|
//
|
||
|
// With following description,
|
||
|
//
|
||
|
// bionic_mountpoint {
|
||
|
// name: "libc.mountpoint",
|
||
|
// stem: "libc.so",
|
||
|
// src: "dummy_mountpoint",
|
||
|
// library: true,
|
||
|
// symlinks: ["libc.so"],
|
||
|
// }
|
||
|
//
|
||
|
// , the build system does following jobs:
|
||
|
//
|
||
|
// A mount point /bionic/lib[64]/libc.so is created. Its content
|
||
|
// is from the file 'dummy_mountpoint'.
|
||
|
//
|
||
|
// Then a symlink is created at /system/lib[64]/libc.so which points to
|
||
|
// the created mountpoint.
|
||
|
//
|
||
|
// At runtime, on the mount point, either bootstrap Bionic or default Bionic
|
||
|
// (which is from the runtime APEX) is mounted by the init process. The
|
||
|
// symlink exists to provide consistent legacy path for compatibility
|
||
|
// reason.
|
||
|
func init() {
|
||
|
android.RegisterModuleType("bionic_mountpoint", bionicMountpointFactory)
|
||
|
}
|
||
|
|
||
|
type bionicMountpoint struct {
|
||
|
android.ModuleBase
|
||
|
properties bionicMountpointProperties
|
||
|
|
||
|
outputFile android.Path
|
||
|
pathInPartition string
|
||
|
stem string
|
||
|
}
|
||
|
|
||
|
type bionicMountpointProperties struct {
|
||
|
// The file that is installed as the mount point
|
||
|
Src *string
|
||
|
|
||
|
// True if the mount point is for a Bionic library such libc.so
|
||
|
Library *bool
|
||
|
// True if the mount point is for a Bionic binary such as linker
|
||
|
Binary *bool
|
||
|
|
||
|
// Base name of the mount point
|
||
|
Stem *string `android:"arch_variant"`
|
||
|
|
||
|
// Append to the name of the output
|
||
|
Suffix *string `android:"arch_variant"`
|
||
|
|
||
|
// Symlinks to the mountpoints from the system and recovery partitions
|
||
|
// Symlinks names will have the same suffix as the mount point
|
||
|
Symlinks []string
|
||
|
}
|
||
|
|
||
|
func (m *bionicMountpoint) DepsMutator(ctx android.BottomUpMutatorContext) {
|
||
|
if Bool(m.properties.Library) == Bool(m.properties.Binary) {
|
||
|
ctx.ModuleErrorf("either binary or library must be set to true")
|
||
|
return
|
||
|
}
|
||
|
if m.properties.Stem == nil {
|
||
|
ctx.PropertyErrorf("stem", "stem must be set")
|
||
|
return
|
||
|
}
|
||
|
if m.properties.Src == nil {
|
||
|
ctx.PropertyErrorf("src", "src must be set")
|
||
|
}
|
||
|
android.ExtractSourceDeps(ctx, m.properties.Src)
|
||
|
}
|
||
|
|
||
|
func (m *bionicMountpoint) GenerateAndroidBuildActions(ctx android.ModuleContext) {
|
||
|
if Bool(m.properties.Library) {
|
||
|
m.pathInPartition = "lib"
|
||
|
if m.Arch().ArchType.Multilib == "lib64" {
|
||
|
m.pathInPartition = "lib64"
|
||
|
}
|
||
|
} else if Bool(m.properties.Binary) {
|
||
|
m.pathInPartition = "bin"
|
||
|
}
|
||
|
|
||
|
m.stem = String(m.properties.Stem) + String(m.properties.Suffix)
|
||
|
|
||
|
m.outputFile = ctx.ExpandSource(String(m.properties.Src), "src")
|
||
|
}
|
||
|
|
||
|
func (m *bionicMountpoint) AndroidMk() android.AndroidMkData {
|
||
|
return android.AndroidMkData {
|
||
|
Custom: func(w io.Writer, name, prefix, moduleDir string, data android.AndroidMkData) {
|
||
|
if !m.Arch().Native {
|
||
|
return
|
||
|
}
|
||
|
fmt.Fprintln(w, "\ninclude $(CLEAR_VARS)")
|
||
|
fmt.Fprintln(w, "LOCAL_PATH :=", moduleDir)
|
||
|
fmt.Fprintln(w, "LOCAL_MODULE :=", name)
|
||
|
fmt.Fprintln(w, "LOCAL_USE_CLANG_LLD := false")
|
||
|
fmt.Fprintln(w, "LOCAL_STRIP_MODULE := false")
|
||
|
if Bool(m.properties.Library) {
|
||
|
fmt.Fprintln(w, "LOCAL_MODULE_CLASS := SHARED_LIBRARIES")
|
||
|
} else if Bool(m.properties.Binary) {
|
||
|
fmt.Fprintln(w, "LOCAL_MODULE_CLASS := EXECUTABLES")
|
||
|
}
|
||
|
fmt.Fprintln(w, "LOCAL_MODULE_TAGS := optional")
|
||
|
fmt.Fprintln(w, "LOCAL_PREBUILT_MODULE_FILE :=", m.outputFile.String())
|
||
|
fmt.Fprintln(w, "LOCAL_MODULE_TARGET_ARCH :=", m.Arch().ArchType.String())
|
||
|
fmt.Fprintln(w, "LOCAL_MODULE_PATH :=", "$(TARGET_ROOT_OUT)/bionic/" + m.pathInPartition)
|
||
|
fmt.Fprintln(w, "LOCAL_INSTALLED_MODULE_STEM :=", m.stem)
|
||
|
|
||
|
if len(m.properties.Symlinks) > 0 {
|
||
|
symlink_dir_in_system := "$(TARGET_OUT)/" + m.pathInPartition + "/"
|
||
|
symlink_dir_in_recovery := "$(TARGET_RECOVERY_ROOT_OUT)/system/" + m.pathInPartition + "/"
|
||
|
symlink_target := "/bionic/" + m.pathInPartition + "/" + m.stem
|
||
|
cmds := []string{}
|
||
|
cmds = append(cmds, "$(hide) mkdir -p " + symlink_dir_in_system)
|
||
|
cmds = append(cmds, "mkdir -p " + symlink_dir_in_recovery)
|
||
|
for _, s := range m.properties.Symlinks {
|
||
|
symlink := s + String(m.properties.Suffix)
|
||
|
cmds = append(cmds, "ln -sf " + symlink_target + " " + symlink_dir_in_system + symlink)
|
||
|
cmds = append(cmds, "ln -sf " + symlink_target + " " + symlink_dir_in_recovery + symlink)
|
||
|
}
|
||
|
fmt.Fprintln(w, "LOCAL_POST_INSTALL_CMD := " + strings.Join(cmds, " && "))
|
||
|
}
|
||
|
fmt.Fprintln(w, "include $(BUILD_PREBUILT)")
|
||
|
},
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func bionicMountpointFactory() android.Module {
|
||
|
m := &bionicMountpoint{}
|
||
|
m.AddProperties(&m.properties)
|
||
|
android.InitAndroidArchModule(m, android.DeviceSupported, android.MultilibBoth)
|
||
|
return m
|
||
|
}
|
||
|
|
||
|
var Bool = proptools.Bool
|
||
|
var String = proptools.String
|