diff options
author | 2024-01-04 14:47:45 -0800 | |
---|---|---|
committer | 2024-01-05 09:54:09 -0800 | |
commit | 3cc3154d33265d956bb1036d1e9a569cf3eb8d4a (patch) | |
tree | 211a6495af9f6e1f680b5806d75f3ee8c6cdfd3f /android/config_bp2build.go | |
parent | d3f7d1a44c2ea75072197b0e610c07216ba92ae2 (diff) |
Remove more bp2build
Bug: 315353489
Test: m blueprint_tests
Change-Id: Ib854fe1a448c258fe086691a6e5ed2d98537f5e4
Diffstat (limited to 'android/config_bp2build.go')
-rw-r--r-- | android/config_bp2build.go | 360 |
1 files changed, 0 insertions, 360 deletions
diff --git a/android/config_bp2build.go b/android/config_bp2build.go index b632e3302..4c2fb5e4a 100644 --- a/android/config_bp2build.go +++ b/android/config_bp2build.go @@ -15,24 +15,11 @@ package android import ( - "fmt" - "reflect" - "regexp" - "sort" "strings" - "android/soong/bazel" - "android/soong/starlark_fmt" - "github.com/google/blueprint" ) -// BazelVarExporter is a collection of configuration variables that can be exported for use in Bazel rules -type BazelVarExporter interface { - // asBazel expands strings of configuration variables into their concrete values - asBazel(Config, ExportedStringVariables, ExportedStringListVariables, ExportedConfigDependingVariables) []bazelConstant -} - // ExportedVariables is a collection of interdependent configuration variables type ExportedVariables struct { // Maps containing toolchain variables that are independent of the @@ -61,18 +48,6 @@ func NewExportedVariables(pctx PackageContext) ExportedVariables { } } -func (ev ExportedVariables) asBazel(config Config, - stringVars ExportedStringVariables, stringListVars ExportedStringListVariables, cfgDepVars ExportedConfigDependingVariables) []bazelConstant { - ret := []bazelConstant{} - ret = append(ret, ev.exportedStringVars.asBazel(config, stringVars, stringListVars, cfgDepVars)...) - ret = append(ret, ev.exportedStringListVars.asBazel(config, stringVars, stringListVars, cfgDepVars)...) - ret = append(ret, ev.exportedStringListDictVars.asBazel(config, stringVars, stringListVars, cfgDepVars)...) - // Note: ExportedVariableReferenceDictVars collections can only contain references to other variables and must be printed last - ret = append(ret, ev.exportedVariableReferenceDictVars.asBazel(config, stringVars, stringListVars, cfgDepVars)...) - ret = append(ret, ev.exportedConfigDependingVars.asBazel(config, stringVars, stringListVars, cfgDepVars)...) - return ret -} - // ExportStringStaticVariable declares a static string variable and exports it to // Bazel's toolchain. func (ev ExportedVariables) ExportStringStaticVariable(name string, value string) { @@ -142,49 +117,6 @@ func (m ExportedConfigDependingVariables) set(k string, v interface{}) { m[k] = v } -func (m ExportedConfigDependingVariables) asBazel(config Config, - stringVars ExportedStringVariables, stringListVars ExportedStringListVariables, cfgDepVars ExportedConfigDependingVariables) []bazelConstant { - ret := make([]bazelConstant, 0, len(m)) - for variable, unevaluatedVar := range m { - evalFunc := reflect.ValueOf(unevaluatedVar) - validateVariableMethod(variable, evalFunc) - evaluatedResult := evalFunc.Call([]reflect.Value{reflect.ValueOf(config)}) - evaluatedValue := evaluatedResult[0].Interface().(string) - expandedVars, err := expandVar(config, evaluatedValue, stringVars, stringListVars, cfgDepVars) - if err != nil { - panic(fmt.Errorf("error expanding config variable %s: %s", variable, err)) - } - if len(expandedVars) > 1 { - ret = append(ret, bazelConstant{ - variableName: variable, - internalDefinition: starlark_fmt.PrintStringList(expandedVars, 0), - }) - } else { - ret = append(ret, bazelConstant{ - variableName: variable, - internalDefinition: fmt.Sprintf(`"%s"`, validateCharacters(expandedVars[0])), - }) - } - } - return ret -} - -// Ensure that string s has no invalid characters to be generated into the bzl file. -func validateCharacters(s string) string { - for _, c := range []string{`\n`, `"`, `\`} { - if strings.Contains(s, c) { - panic(fmt.Errorf("%s contains illegal character %s", s, c)) - } - } - return s -} - -type bazelConstant struct { - variableName string - internalDefinition string - sortLast bool -} - // ExportedStringVariables is a mapping of variable names to string values type ExportedStringVariables map[string]string @@ -192,25 +124,6 @@ func (m ExportedStringVariables) set(k string, v string) { m[k] = v } -func (m ExportedStringVariables) asBazel(config Config, - stringVars ExportedStringVariables, stringListVars ExportedStringListVariables, cfgDepVars ExportedConfigDependingVariables) []bazelConstant { - ret := make([]bazelConstant, 0, len(m)) - for k, variableValue := range m { - expandedVar, err := expandVar(config, variableValue, stringVars, stringListVars, cfgDepVars) - if err != nil { - panic(fmt.Errorf("error expanding config variable %s: %s", k, err)) - } - if len(expandedVar) > 1 { - panic(fmt.Errorf("%q expands to more than one string value: %q", variableValue, expandedVar)) - } - ret = append(ret, bazelConstant{ - variableName: k, - internalDefinition: fmt.Sprintf(`"%s"`, validateCharacters(expandedVar[0])), - }) - } - return ret -} - // ExportedStringListVariables is a mapping of variable names to a list of strings type ExportedStringListVariables map[string][]string @@ -218,32 +131,6 @@ func (m ExportedStringListVariables) set(k string, v []string) { m[k] = v } -func (m ExportedStringListVariables) asBazel(config Config, - stringScope ExportedStringVariables, stringListScope ExportedStringListVariables, - exportedVars ExportedConfigDependingVariables) []bazelConstant { - ret := make([]bazelConstant, 0, len(m)) - // For each exported variable, recursively expand elements in the variableValue - // list to ensure that interpolated variables are expanded according to their values - // in the variable scope. - for k, variableValue := range m { - var expandedVars []string - for _, v := range variableValue { - expandedVar, err := expandVar(config, v, stringScope, stringListScope, exportedVars) - if err != nil { - panic(fmt.Errorf("Error expanding config variable %s=%s: %s", k, v, err)) - } - expandedVars = append(expandedVars, expandedVar...) - } - // Assign the list as a bzl-private variable; this variable will be exported - // out through a constants struct later. - ret = append(ret, bazelConstant{ - variableName: k, - internalDefinition: starlark_fmt.PrintStringList(expandedVars, 0), - }) - } - return ret -} - // ExportedStringListDictVariables is a mapping from variable names to a // dictionary which maps keys to lists of strings type ExportedStringListDictVariables map[string]map[string][]string @@ -252,19 +139,6 @@ func (m ExportedStringListDictVariables) set(k string, v map[string][]string) { m[k] = v } -// Since dictionaries are not supported in Ninja, we do not expand variables for dictionaries -func (m ExportedStringListDictVariables) asBazel(_ Config, _ ExportedStringVariables, - _ ExportedStringListVariables, _ ExportedConfigDependingVariables) []bazelConstant { - ret := make([]bazelConstant, 0, len(m)) - for k, dict := range m { - ret = append(ret, bazelConstant{ - variableName: k, - internalDefinition: starlark_fmt.PrintStringListDict(dict, 0), - }) - } - return ret -} - // ExportedVariableReferenceDictVariables is a mapping from variable names to a // dictionary which references previously defined variables. This is used to // create a Starlark output such as: @@ -281,237 +155,3 @@ type ExportedVariableReferenceDictVariables map[string]map[string]string func (m ExportedVariableReferenceDictVariables) set(k string, v map[string]string) { m[k] = v } - -func (m ExportedVariableReferenceDictVariables) asBazel(_ Config, _ ExportedStringVariables, - _ ExportedStringListVariables, _ ExportedConfigDependingVariables) []bazelConstant { - ret := make([]bazelConstant, 0, len(m)) - for n, dict := range m { - for k, v := range dict { - matches, err := variableReference(v) - if err != nil { - panic(err) - } else if !matches.matches { - panic(fmt.Errorf("Expected a variable reference, got %q", v)) - } else if len(matches.fullVariableReference) != len(v) { - panic(fmt.Errorf("Expected only a variable reference, got %q", v)) - } - dict[k] = "_" + matches.variable - } - ret = append(ret, bazelConstant{ - variableName: n, - internalDefinition: starlark_fmt.PrintDict(dict, 0), - sortLast: true, - }) - } - return ret -} - -// BazelToolchainVars expands an ExportedVariables collection and returns a string -// of formatted Starlark variable definitions -func BazelToolchainVars(config Config, exportedVars ExportedVariables) string { - results := exportedVars.asBazel( - config, - exportedVars.exportedStringVars, - exportedVars.exportedStringListVars, - exportedVars.exportedConfigDependingVars, - ) - - sort.Slice(results, func(i, j int) bool { - if results[i].sortLast != results[j].sortLast { - return !results[i].sortLast - } - return results[i].variableName < results[j].variableName - }) - - definitions := make([]string, 0, len(results)) - constants := make([]string, 0, len(results)) - for _, b := range results { - definitions = append(definitions, - fmt.Sprintf("_%s = %s", b.variableName, b.internalDefinition)) - constants = append(constants, - fmt.Sprintf("%[1]s%[2]s = _%[2]s,", starlark_fmt.Indention(1), b.variableName)) - } - - // Build the exported constants struct. - ret := bazel.GeneratedBazelFileWarning - ret += "\n\n" - ret += strings.Join(definitions, "\n\n") - ret += "\n\n" - ret += "constants = struct(\n" - ret += strings.Join(constants, "\n") - ret += "\n)" - - return ret -} - -type match struct { - matches bool - fullVariableReference string - variable string -} - -func variableReference(input string) (match, error) { - // e.g. "${ExternalCflags}" - r := regexp.MustCompile(`\${(?:config\.)?([a-zA-Z0-9_]+)}`) - - matches := r.FindStringSubmatch(input) - if len(matches) == 0 { - return match{}, nil - } - if len(matches) != 2 { - return match{}, fmt.Errorf("Expected to only match 1 subexpression in %s, got %d", input, len(matches)-1) - } - return match{ - matches: true, - fullVariableReference: matches[0], - // Index 1 of FindStringSubmatch contains the subexpression match - // (variable name) of the capture group. - variable: matches[1], - }, nil -} - -// expandVar recursively expand interpolated variables in the exportedVars scope. -// -// We're using a string slice to track the seen variables to avoid -// stackoverflow errors with infinite recursion. it's simpler to use a -// string slice than to handle a pass-by-referenced map, which would make it -// quite complex to track depth-first interpolations. It's also unlikely the -// interpolation stacks are deep (n > 1). -func expandVar(config Config, toExpand string, stringScope ExportedStringVariables, - stringListScope ExportedStringListVariables, exportedVars ExportedConfigDependingVariables) ([]string, error) { - - // Internal recursive function. - var expandVarInternal func(string, map[string]bool) (string, error) - expandVarInternal = func(toExpand string, seenVars map[string]bool) (string, error) { - var ret string - remainingString := toExpand - for len(remainingString) > 0 { - matches, err := variableReference(remainingString) - if err != nil { - panic(err) - } - if !matches.matches { - return ret + remainingString, nil - } - matchIndex := strings.Index(remainingString, matches.fullVariableReference) - ret += remainingString[:matchIndex] - remainingString = remainingString[matchIndex+len(matches.fullVariableReference):] - - variable := matches.variable - // toExpand contains a variable. - if _, ok := seenVars[variable]; ok { - return ret, fmt.Errorf( - "Unbounded recursive interpolation of variable: %s", variable) - } - // A map is passed-by-reference. Create a new map for - // this scope to prevent variables seen in one depth-first expansion - // to be also treated as "seen" in other depth-first traversals. - newSeenVars := map[string]bool{} - for k := range seenVars { - newSeenVars[k] = true - } - newSeenVars[variable] = true - if unexpandedVars, ok := stringListScope[variable]; ok { - expandedVars := []string{} - for _, unexpandedVar := range unexpandedVars { - expandedVar, err := expandVarInternal(unexpandedVar, newSeenVars) - if err != nil { - return ret, err - } - expandedVars = append(expandedVars, expandedVar) - } - ret += strings.Join(expandedVars, " ") - } else if unexpandedVar, ok := stringScope[variable]; ok { - expandedVar, err := expandVarInternal(unexpandedVar, newSeenVars) - if err != nil { - return ret, err - } - ret += expandedVar - } else if unevaluatedVar, ok := exportedVars[variable]; ok { - evalFunc := reflect.ValueOf(unevaluatedVar) - validateVariableMethod(variable, evalFunc) - evaluatedResult := evalFunc.Call([]reflect.Value{reflect.ValueOf(config)}) - evaluatedValue := evaluatedResult[0].Interface().(string) - expandedVar, err := expandVarInternal(evaluatedValue, newSeenVars) - if err != nil { - return ret, err - } - ret += expandedVar - } else { - return "", fmt.Errorf("Unbound config variable %s", variable) - } - } - return ret, nil - } - var ret []string - stringFields := splitStringKeepingQuotedSubstring(toExpand, ' ') - for _, v := range stringFields { - val, err := expandVarInternal(v, map[string]bool{}) - if err != nil { - return ret, err - } - ret = append(ret, val) - } - - return ret, nil -} - -// splitStringKeepingQuotedSubstring splits a string on a provided separator, -// but it will not split substrings inside unescaped double quotes. If the double -// quotes are escaped, then the returned string will only include the quote, and -// not the escape. -func splitStringKeepingQuotedSubstring(s string, delimiter byte) []string { - var ret []string - quote := byte('"') - - var substring []byte - quoted := false - escaped := false - - for i := range s { - if !quoted && s[i] == delimiter { - ret = append(ret, string(substring)) - substring = []byte{} - continue - } - - characterIsEscape := i < len(s)-1 && s[i] == '\\' && s[i+1] == quote - if characterIsEscape { - escaped = true - continue - } - - if s[i] == quote { - if !escaped { - quoted = !quoted - } - escaped = false - } - - substring = append(substring, s[i]) - } - - ret = append(ret, string(substring)) - - return ret -} - -func validateVariableMethod(name string, methodValue reflect.Value) { - methodType := methodValue.Type() - if methodType.Kind() != reflect.Func { - panic(fmt.Errorf("method given for variable %s is not a function", - name)) - } - if n := methodType.NumIn(); n != 1 { - panic(fmt.Errorf("method for variable %s has %d inputs (should be 1)", - name, n)) - } - if n := methodType.NumOut(); n != 1 { - panic(fmt.Errorf("method for variable %s has %d outputs (should be 1)", - name, n)) - } - if kind := methodType.Out(0).Kind(); kind != reflect.String { - panic(fmt.Errorf("method for variable %s does not return a string", - name)) - } -} |