"[]cmd/compile/internal/ssa.ID %v": "",
"[]string %v": "",
"bool %v": "",
- "byte %02x": "",
"byte %08b": "",
"byte %c": "",
"cmd/compile/internal/arm.shift %d": "",
package gc
import (
- "bytes"
"cmd/compile/internal/types"
"cmd/internal/objabi"
"cmd/internal/src"
return nil
}
-// Convert raw string to the prefix that will be used in the symbol
-// table. All control characters, space, '%' and '"', as well as
-// non-7-bit clean bytes turn into %xx. The period needs escaping
-// only in the last segment of the path, and it makes for happier
-// users if we escape that as little as possible.
-//
-// If you edit this, edit ../../debug/goobj/read.go:/importPathToPrefix too.
-func pathtoprefix(s string) string {
- slash := strings.LastIndex(s, "/")
- for i := 0; i < len(s); i++ {
- c := s[i]
- if c <= ' ' || i >= slash && c == '.' || c == '%' || c == '"' || c >= 0x7F {
- var buf bytes.Buffer
- for i := 0; i < len(s); i++ {
- c := s[i]
- if c <= ' ' || i >= slash && c == '.' || c == '%' || c == '"' || c >= 0x7F {
- fmt.Fprintf(&buf, "%%%02x", c)
- continue
- }
- buf.WriteByte(c)
- }
- return buf.String()
- }
- }
- return s
-}
-
var pkgMap = make(map[string]*types.Pkg)
var pkgs []*types.Pkg
p := new(types.Pkg)
p.Path = path
- p.Prefix = pathtoprefix(path)
+ p.Prefix = objabi.PathToPrefix(path)
p.Syms = make(map[string]*types.Sym)
pkgMap[path] = p
pkgs = append(pkgs, p)
pkgprefix string
}
-// importPathToPrefix returns the prefix that will be used in the
-// final symbol table for the given import path.
-// We escape '%', '"', all control characters and non-ASCII bytes,
-// and any '.' after the final slash.
-//
-// See ../../../cmd/ld/lib.c:/^pathtoprefix and
-// ../../../cmd/gc/subr.c:/^pathtoprefix.
-func importPathToPrefix(s string) string {
- // find index of last slash, if any, or else -1.
- // used for determining whether an index is after the last slash.
- slash := strings.LastIndex(s, "/")
-
- // check for chars that need escaping
- n := 0
- for r := 0; r < len(s); r++ {
- if c := s[r]; c <= ' ' || (c == '.' && r > slash) || c == '%' || c == '"' || c >= 0x7F {
- n++
- }
- }
-
- // quick exit
- if n == 0 {
- return s
- }
-
- // escape
- const hex = "0123456789abcdef"
- p := make([]byte, 0, len(s)+2*n)
- for r := 0; r < len(s); r++ {
- if c := s[r]; c <= ' ' || (c == '.' && r > slash) || c == '%' || c == '"' || c >= 0x7F {
- p = append(p, '%', hex[c>>4], hex[c&0xF])
- } else {
- p = append(p, c)
- }
- }
-
- return string(p)
-}
-
// init initializes r to read package p from f.
func (r *objReader) init(f io.ReadSeeker, p *Package) {
r.f = f
r.limit, _ = f.Seek(0, io.SeekEnd)
f.Seek(r.offset, io.SeekStart)
r.b = bufio.NewReader(f)
- r.pkgprefix = importPathToPrefix(p.ImportPath) + "."
+ r.pkgprefix = objabi.PathToPrefix(p.ImportPath) + "."
}
// error records that an error occurred.
+++ /dev/null
-// Copyright 2013 The Go Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style
-// license that can be found in the LICENSE file.
-
-package goobj
-
-import "testing"
-
-var importPathToPrefixTests = []struct {
- in string
- out string
-}{
- {"runtime", "runtime"},
- {"sync/atomic", "sync/atomic"},
- {"golang.org/x/tools/godoc", "golang.org/x/tools/godoc"},
- {"foo.bar/baz.quux", "foo.bar/baz%2equux"},
- {"", ""},
- {"%foo%bar", "%25foo%25bar"},
- {"\x01\x00\x7F☺", "%01%00%7f%e2%98%ba"},
-}
-
-func TestImportPathToPrefix(t *testing.T) {
- for _, tt := range importPathToPrefixTests {
- if out := importPathToPrefix(tt.in); out != tt.out {
- t.Errorf("importPathToPrefix(%q) = %q, want %q", tt.in, out, tt.out)
- }
- }
-}
--- /dev/null
+// Copyright 2017 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package objabi
+
+import "strings"
+
+// PathToPrefix converts raw string to the prefix that will be used in the
+// symbol table. All control characters, space, '%' and '"', as well as
+// non-7-bit clean bytes turn into %xx. The period needs escaping only in the
+// last segment of the path, and it makes for happier users if we escape that as
+// little as possible.
+func PathToPrefix(s string) string {
+ slash := strings.LastIndex(s, "/")
+ // check for chars that need escaping
+ n := 0
+ for r := 0; r < len(s); r++ {
+ if c := s[r]; c <= ' ' || (c == '.' && r > slash) || c == '%' || c == '"' || c >= 0x7F {
+ n++
+ }
+ }
+
+ // quick exit
+ if n == 0 {
+ return s
+ }
+
+ // escape
+ const hex = "0123456789abcdef"
+ p := make([]byte, 0, len(s)+2*n)
+ for r := 0; r < len(s); r++ {
+ if c := s[r]; c <= ' ' || (c == '.' && r > slash) || c == '%' || c == '"' || c >= 0x7F {
+ p = append(p, '%', hex[c>>4], hex[c&0xF])
+ } else {
+ p = append(p, c)
+ }
+ }
+
+ return string(p)
+}
--- /dev/null
+// Copyright 2017 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package objabi
+
+import "testing"
+
+func TestPathToPrefix(t *testing.T) {
+ tests := []struct {
+ Path string
+ Expected string
+ }{{"foo/bar/v1", "foo/bar/v1"},
+ {"foo/bar/v.1", "foo/bar/v%2e1"},
+ {"f.o.o/b.a.r/v1", "f.o.o/b.a.r/v1"},
+ {"f.o.o/b.a.r/v.1", "f.o.o/b.a.r/v%2e1"},
+ {"f.o.o/b.a.r/v..1", "f.o.o/b.a.r/v%2e%2e1"},
+ {"f.o.o/b.a.r/v..1.", "f.o.o/b.a.r/v%2e%2e1%2e"},
+ {"f.o.o/b.a.r/v%1", "f.o.o/b.a.r/v%251"},
+ {"runtime", "runtime"},
+ {"sync/atomic", "sync/atomic"},
+ {"golang.org/x/tools/godoc", "golang.org/x/tools/godoc"},
+ {"foo.bar/baz.quux", "foo.bar/baz%2equux"},
+ {"", ""},
+ {"%foo%bar", "%25foo%25bar"},
+ {"\x01\x00\x7F☺", "%01%00%7f%e2%98%ba"},
+ }
+ for _, tc := range tests {
+ if got := PathToPrefix(tc.Path); got != tc.Expected {
+ t.Errorf("expected PathToPrefix(%s) = %s, got %s", tc.Path, tc.Expected, got)
+ }
+ }
+}
if eq < 0 || dot < 0 {
Exitf("-X flag requires argument of the form importpath.name=value")
}
- addstrdata(ctxt, pathtoprefix(arg[:dot])+arg[dot:eq], arg[eq+1:])
+ addstrdata(ctxt, objabi.PathToPrefix(arg[:dot])+arg[dot:eq], arg[eq+1:])
}
func addstrdata(ctxt *Link, name string, value string) {
// first containing package that the linker loads). canonicalize
// it here to the package with which it will be laid down
// in text.
- s.File = pathtoprefix(lib.Pkg)
+ s.File = objabi.PathToPrefix(lib.Pkg)
}
}
}
}
func objfile(ctxt *Link, lib *Library) {
- pkg := pathtoprefix(lib.Pkg)
+ pkg := objabi.PathToPrefix(lib.Pkg)
if ctxt.Debugvlog > 1 {
ctxt.Logf("%5.2f ldobj: %s (%s)\n", Cputime(), lib.File, pkg)
// compiled by a non-Go compiler) it returns the Hostobj pointer. If
// it is a Go object, it returns nil.
func ldobj(ctxt *Link, f *bio.Reader, lib *Library, length int64, pn string, file string, whence int) *Hostobj {
- pkg := pathtoprefix(lib.Pkg)
+ pkg := objabi.PathToPrefix(lib.Pkg)
eof := f.Offset() + length
start := f.Offset()
ctxt.Shlibs = append(ctxt.Shlibs, Shlib{Path: libpath, Hash: hash, Deps: deps, File: f, gcdataAddresses: gcdataAddresses})
}
-// Copied from ../gc/subr.c:/^pathtoprefix; must stay in sync.
-/*
- * Convert raw string to the prefix that will be used in the symbol table.
- * Invalid bytes turn into %xx. Right now the only bytes that need
- * escaping are %, ., and ", but we escape all control characters too.
- *
- * If you edit this, edit ../gc/subr.c:/^pathtoprefix too.
- * If you edit this, edit ../../debug/goobj/read.go:/importPathToPrefix too.
- */
-func pathtoprefix(s string) string {
- slash := strings.LastIndex(s, "/")
- for i := 0; i < len(s); i++ {
- c := s[i]
- if c <= ' ' || i >= slash && c == '.' || c == '%' || c == '"' || c >= 0x7F {
- var buf bytes.Buffer
- for i := 0; i < len(s); i++ {
- c := s[i]
- if c <= ' ' || i >= slash && c == '.' || c == '%' || c == '"' || c >= 0x7F {
- fmt.Fprintf(&buf, "%%%02x", c)
- continue
- }
- buf.WriteByte(c)
- }
- return buf.String()
- }
- }
- return s
-}
-
func addsection(seg *Segment, name string, rwx int) *Section {
sect := new(Section)
sect.Rwx = uint8(rwx)
}
func (r *objReader) loadObjFile() {
- pkg := pathtoprefix(r.lib.Pkg)
+ pkg := objabi.PathToPrefix(r.lib.Pkg)
// Magic header
var buf [8]uint8
typ := r.readSymIndex()
data := r.readData()
nreloc := r.readInt()
- pkg := pathtoprefix(r.lib.Pkg)
+ pkg := objabi.PathToPrefix(r.lib.Pkg)
isdup := false
var dup *Symbol
if p == -1 {
return
}
- pkgprefix := []byte(pathtoprefix(r.lib.Pkg) + ".")
+ pkgprefix := []byte(objabi.PathToPrefix(r.lib.Pkg) + ".")
patched := bytes.Replace(s.P[:e], emptyPkg, pkgprefix, -1)
s.P = append(patched, s.P[e:]...)
// readSymName reads a symbol name, replacing all "". with pkg.
func (r *objReader) readSymName() string {
- pkg := pathtoprefix(r.lib.Pkg)
+ pkg := objabi.PathToPrefix(r.lib.Pkg)
n := r.readInt()
if n == 0 {
r.readInt64()