mirror of
https://github.com/golang/go
synced 2024-11-19 10:04:56 -07:00
cmd/compile: allow deduplication of long strings
String symbols' names used to appear in the final binary. Using a string's contents as it's symbol's name was a thus a bad idea if the string's name was long. Recent improvements by crawshaw have changed that. Instead of placing long strings behind opaque names in local packages, place them in the global string package and make them content-addressable. Symbol names still occur in the object files, so use a hash to avoid needless length there. Reduces the size of cmd/go by 30k. Change-Id: Ifdbbaf47bf44352418c90ddd903d5106e48db4f1 Reviewed-on: https://go-review.googlesource.com/20524 Run-TryBot: Josh Bleecher Snyder <josharian@gmail.com> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: David Crawshaw <crawshaw@golang.org>
This commit is contained in:
parent
13f74db304
commit
a0232ea0dd
@ -6,7 +6,9 @@ package gc
|
||||
|
||||
import (
|
||||
"cmd/internal/obj"
|
||||
"crypto/sha256"
|
||||
"fmt"
|
||||
"io"
|
||||
"strconv"
|
||||
)
|
||||
|
||||
@ -181,27 +183,22 @@ func duintptr(s *Sym, off int, v uint64) int {
|
||||
return duintxx(s, off, v, Widthptr)
|
||||
}
|
||||
|
||||
var stringsym_gen int
|
||||
|
||||
func stringsym(s string) (hdr, data *Sym) {
|
||||
var symname string
|
||||
var pkg *Pkg
|
||||
if len(s) > 100 {
|
||||
// huge strings are made static to avoid long names
|
||||
stringsym_gen++
|
||||
symname = fmt.Sprintf(".gostring.%d", stringsym_gen)
|
||||
|
||||
pkg = localpkg
|
||||
// Huge strings are hashed to avoid long names in object files.
|
||||
// Indulge in some paranoia by writing the length of s, too,
|
||||
// as protection against length extension attacks.
|
||||
h := sha256.New()
|
||||
io.WriteString(h, s)
|
||||
symname = fmt.Sprintf(".gostring.%d.%x", len(s), h.Sum(nil))
|
||||
} else {
|
||||
// small strings get named by their contents,
|
||||
// so that multiple modules using the same string
|
||||
// can share it.
|
||||
// Small strings get named directly by their contents.
|
||||
symname = strconv.Quote(s)
|
||||
pkg = gostringpkg
|
||||
}
|
||||
|
||||
symhdr := Pkglookup("hdr."+symname, pkg)
|
||||
symdata := Pkglookup(symname, pkg)
|
||||
symhdr := Pkglookup("hdr."+symname, gostringpkg)
|
||||
symdata := Pkglookup(symname, gostringpkg)
|
||||
|
||||
// SymUniq flag indicates that data is generated already
|
||||
if symhdr.Flags&SymUniq != 0 {
|
||||
|
Loading…
Reference in New Issue
Block a user