mirror of
https://github.com/golang/go
synced 2024-11-26 15:06:52 -07:00
plugin: resolve plugin import path issue
Resolve import paths to get plugin symbol prefixes. Fixes #19534 Change-Id: Ic25d83e72465ba8f6be0337218a1627b5dc702dc Reviewed-on: https://go-review.googlesource.com/40994 Run-TryBot: Todd Neal <todd@tneal.org> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: David Crawshaw <crawshaw@golang.org>
This commit is contained in:
parent
819d1cce6e
commit
7a92395ddd
23
misc/cgo/testplugin/src/issue19534/main.go
Normal file
23
misc/cgo/testplugin/src/issue19534/main.go
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
// 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 main
|
||||||
|
|
||||||
|
import "plugin"
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
p, err := plugin.Open("plugin.so")
|
||||||
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
sym, err := p.Lookup("Foo")
|
||||||
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
f := sym.(func() int)
|
||||||
|
if f() != 42 {
|
||||||
|
panic("expected f() == 42")
|
||||||
|
}
|
||||||
|
}
|
9
misc/cgo/testplugin/src/issue19534/plugin.go
Normal file
9
misc/cgo/testplugin/src/issue19534/plugin.go
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
// 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 main
|
||||||
|
|
||||||
|
func Foo() int {
|
||||||
|
return 42
|
||||||
|
}
|
@ -16,7 +16,7 @@ goarch=$(go env GOARCH)
|
|||||||
|
|
||||||
function cleanup() {
|
function cleanup() {
|
||||||
rm -f plugin*.so unnamed*.so iface*.so
|
rm -f plugin*.so unnamed*.so iface*.so
|
||||||
rm -rf host pkg sub iface issue18676
|
rm -rf host pkg sub iface issue18676 issue19534
|
||||||
}
|
}
|
||||||
trap cleanup EXIT
|
trap cleanup EXIT
|
||||||
|
|
||||||
@ -44,3 +44,9 @@ LD_LIBRARY_PATH=$(pwd) ./iface
|
|||||||
GOPATH=$(pwd) go build -buildmode=plugin -o plugin.so src/issue18676/plugin.go
|
GOPATH=$(pwd) go build -buildmode=plugin -o plugin.so src/issue18676/plugin.go
|
||||||
GOPATH=$(pwd) go build -o issue18676 src/issue18676/main.go
|
GOPATH=$(pwd) go build -o issue18676 src/issue18676/main.go
|
||||||
timeout 10s ./issue18676
|
timeout 10s ./issue18676
|
||||||
|
|
||||||
|
# Test for issue 19534 - that we can load a plugin built in a path with non-alpha
|
||||||
|
# characters
|
||||||
|
GOPATH=$(pwd) go build -buildmode=plugin -ldflags='-pluginpath=issue.19534' -o plugin.so src/issue19534/plugin.go
|
||||||
|
GOPATH=$(pwd) go build -o issue19534 src/issue19534/main.go
|
||||||
|
./issue19534
|
||||||
|
@ -39,6 +39,47 @@ import (
|
|||||||
"unsafe"
|
"unsafe"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// avoid a dependency on strings
|
||||||
|
func lastIndexByte(s string, c byte) int {
|
||||||
|
for i := len(s) - 1; i >= 0; i-- {
|
||||||
|
if s[i] == c {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1
|
||||||
|
}
|
||||||
|
|
||||||
|
// pathToPrefix converts raw string to the prefix that will be used in the symbol
|
||||||
|
// table. If modifying, modify the version in internal/obj/sym.go as well.
|
||||||
|
func pathToPrefix(s string) string {
|
||||||
|
slash := lastIndexByte(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)
|
||||||
|
}
|
||||||
|
|
||||||
func open(name string) (*Plugin, error) {
|
func open(name string) (*Plugin, error) {
|
||||||
cPath := (*C.char)(C.malloc(C.PATH_MAX + 1))
|
cPath := (*C.char)(C.malloc(C.PATH_MAX + 1))
|
||||||
defer C.free(unsafe.Pointer(cPath))
|
defer C.free(unsafe.Pointer(cPath))
|
||||||
@ -103,7 +144,7 @@ func open(name string) (*Plugin, error) {
|
|||||||
delete(syms, symName)
|
delete(syms, symName)
|
||||||
symName = symName[1:]
|
symName = symName[1:]
|
||||||
}
|
}
|
||||||
cname := C.CString(pluginpath + "." + symName)
|
cname := C.CString(pathToPrefix(pluginpath) + "." + symName)
|
||||||
p := C.pluginLookup(h, cname, &cErr)
|
p := C.pluginLookup(h, cname, &cErr)
|
||||||
C.free(unsafe.Pointer(cname))
|
C.free(unsafe.Pointer(cname))
|
||||||
if p == nil {
|
if p == nil {
|
||||||
|
Loading…
Reference in New Issue
Block a user