File: headers.go

package info (click to toggle)
golang-android-soong 0.0~git20201014.17e97d9-4
  • links: PTS, VCS
  • area: main
  • in suites: bookworm, forky, sid, trixie
  • size: 7,680 kB
  • sloc: python: 3,000; sh: 1,780; cpp: 66; makefile: 5
file content (120 lines) | stat: -rw-r--r-- 2,685 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
package extensions

import (
	"strings"

	"github.com/google/blueprint/parser"

	"android/soong/bpfix/bpfix"
)

var fixSteps = bpfix.FixStepsExtension{
	Name: "partner-include-dirs",
	Steps: []bpfix.FixStep{
		{
			Name: "fixIncludeDirs",
			Fix:  fixIncludeDirs,
		},
	},
}

func init() {
	bpfix.RegisterFixStepExtension(&fixSteps)
}

type includeDirFix struct {
	libName  string
	libType  string
	variable string
	subdir   string
}

var commonIncludeDirs = []includeDirFix{
	{
		libName:  "my_header_lib",
		libType:  "header_libs",
		variable: "TARGET_OUT_HEADERS",
		subdir:   "/my_headers",
	},
}

func findHeaderLib(e parser.Expression) (*includeDirFix, bool) {
	if op, ok := e.(*parser.Operator); ok {
		if op.Operator != '+' {
			return nil, false
		}
		arg0, ok := op.Args[0].(*parser.Variable)
		arg1, ok1 := op.Args[1].(*parser.String)
		if !ok || !ok1 {
			return nil, false
		}
		for _, lib := range commonIncludeDirs {
			if arg0.Name == lib.variable && arg1.Value == lib.subdir {
				return &lib, true
			}
		}
	}
	return nil, false
}
func searchThroughOperatorList(mod *parser.Module, e parser.Expression) {
	if list, ok := e.(*parser.List); ok {
		newList := make([]parser.Expression, 0, len(list.Values))
		for _, item := range list.Values {
			if lib, found := findHeaderLib(item); found {
				if lib.libName != "" {
					addLibrary(mod, lib.libType, lib.libName)
				}
			} else {
				newList = append(newList, item)
			}
		}
		list.Values = newList
	}
	if op, ok := e.(*parser.Operator); ok {
		searchThroughOperatorList(mod, op.Args[0])
		searchThroughOperatorList(mod, op.Args[1])
	}
}
func getLiteralListProperty(mod *parser.Module, name string) (list *parser.List, found bool) {
	prop, ok := mod.GetProperty(name)
	if !ok {
		return nil, false
	}
	list, ok = prop.Value.(*parser.List)
	return list, ok
}
func addLibrary(mod *parser.Module, libType string, libName string) {
	var list, ok = getLiteralListProperty(mod, libType)
	if !ok {
		list = new(parser.List)
		prop := new(parser.Property)
		prop.Name = libType
		prop.Value = list
		mod.Properties = append(mod.Properties, prop)
	} else {
		for _, v := range list.Values {
			if stringValue, ok := v.(*parser.String); ok && stringValue.Value == libName {
				return
			}
		}
	}
	lib := new(parser.String)
	lib.Value = libName
	list.Values = append(list.Values, lib)
}
func fixIncludeDirs(f *bpfix.Fixer) error {
	tree := f.Tree()
	for _, def := range tree.Defs {
		mod, ok := def.(*parser.Module)
		if !ok {
			continue
		}
		if !strings.HasPrefix(mod.Type, "cc_") {
			continue
		}
		if prop, ok := mod.GetProperty("include_dirs"); ok {
			searchThroughOperatorList(mod, prop.Value)
		}
	}
	return nil
}