aboutsummaryrefslogtreecommitdiffstats
path: root/prog
diff options
context:
space:
mode:
authorDmitry Vyukov <dvyukov@google.com>2017-12-13 11:58:10 +0100
committerDmitry Vyukov <dvyukov@google.com>2017-12-17 11:39:14 +0100
commit9150b3e5442f9e9ebc53ef5d5a2cd00f01e6f118 (patch)
tree83821b735ea98a654dc6c23d6c75aa13d240a77b /prog
parent0da2fed84fb002e744806a36bddaf6787094e4a5 (diff)
prog: lazily initialize targets
We now have a bunch of targets compiled into each binary. All targets are initialized eagerly on startup time. As the result a do nothing binary starts for ~0.58s and consumes ~21MB. Initialize targets lazily. Usually only 1 target is used. This reduces startup time to ~0.00s and memory consumption to ~5.4MB.
Diffstat (limited to 'prog')
-rw-r--r--prog/target.go23
1 files changed, 16 insertions, 7 deletions
diff --git a/prog/target.go b/prog/target.go
index 4563f107d..29fb100a6 100644
--- a/prog/target.go
+++ b/prog/target.go
@@ -7,6 +7,7 @@ import (
"fmt"
"math/rand"
"sort"
+ "sync"
)
// Target describes target OS/arch pair.
@@ -52,6 +53,8 @@ type Target struct {
StringDictionary []string
// Filled by prog package:
+ init sync.Once
+ initArch func(target *Target)
SyscallMap map[string]*Syscall
ConstMap map[string]uint64
resourceMap map[string]*ResourceDesc
@@ -66,10 +69,7 @@ func RegisterTarget(target *Target, initArch func(target *Target)) {
if targets[key] != nil {
panic(fmt.Sprintf("duplicate target %v", key))
}
- target.SanitizeCall = func(c *Call) {}
- initTarget(target)
- initArch(target)
- target.ConstMap = nil // currently used only by initArch
+ target.initArch = initArch
targets[key] = target
}
@@ -84,13 +84,15 @@ func GetTarget(OS, arch string) (*Target, error) {
sort.Strings(supported)
return nil, fmt.Errorf("unknown target: %v (supported: %v)", key, supported)
}
+ target.init.Do(target.lazyInit)
return target, nil
}
func AllTargets() []*Target {
var res []*Target
- for _, t := range targets {
- res = append(res, t)
+ for _, target := range targets {
+ target.init.Do(target.lazyInit)
+ res = append(res, target)
}
sort.Slice(res, func(i, j int) bool {
if res[i].OS != res[j].OS {
@@ -101,7 +103,14 @@ func AllTargets() []*Target {
return res
}
-func initTarget(target *Target) {
+func (target *Target) lazyInit() {
+ target.SanitizeCall = func(c *Call) {}
+ target.initTarget()
+ target.initArch(target)
+ target.ConstMap = nil // currently used only by initArch
+}
+
+func (target *Target) initTarget() {
target.ConstMap = make(map[string]uint64)
for _, c := range target.Consts {
target.ConstMap[c.Name] = c.Value