diff options
| author | Russ Cox <rsc@golang.org> | 2014-10-28 21:52:53 -0400 |
|---|---|---|
| committer | Russ Cox <rsc@golang.org> | 2014-10-28 21:52:53 -0400 |
| commit | 5e568545991cb358a8a004b21e23ac6fa9801124 (patch) | |
| tree | ac094c574d3f32f9eca8c2c253e5a2ed5b4d230a /src/runtime | |
| parent | 5f54f06a359f2973521ff3f42899c12d3a6a7fed (diff) | |
| download | go-5e568545991cb358a8a004b21e23ac6fa9801124.tar.xz | |
cmd/gc: avoid use of goprintf
goprintf is a printf-like print for Go.
It is used in the code generated by 'defer print(...)' and 'go print(...)'.
Normally print(1, 2, 3) turns into
printint(1)
printint(2)
printint(3)
but defer and go need a single function call to give the runtime;
they give the runtime something like goprintf("%d%d%d", 1, 2, 3).
Variadic functions like goprintf cannot be described in the new
type information world, so we have to replace it.
Replace with a custom function, so that defer print(1, 2, 3) turns
into
defer func(a1, a2, a3 int) {
print(a1, a2, a3)
}(1, 2, 3)
(and then the print becomes three different printints as usual).
Fixes #8614.
LGTM=austin
R=austin
CC=golang-codereviews, r
https://golang.org/cl/159700043
Diffstat (limited to 'src/runtime')
| -rw-r--r-- | src/runtime/print1.go | 27 |
1 files changed, 6 insertions, 21 deletions
diff --git a/src/runtime/print1.go b/src/runtime/print1.go index 0fa1fb63c4..8f8268873b 100644 --- a/src/runtime/print1.go +++ b/src/runtime/print1.go @@ -19,32 +19,17 @@ func bytes(s string) (ret []byte) { return } -// goprintf is the function call that is actually deferred when you write -// defer print(...) -// It is otherwise unused. In particular it is not used for ordinary prints. -// Right now a dynamically allocated string that is being passed as an -// argument is invisible to the garbage collector and might be collected -// if that argument list is the only reference. For now we ignore that possibility. -// To fix, we should change to defer a call to vprintf with a pointer to -// an argument list on the stack, stored in an appropriately typed -// struct. golang.org/issue/8614. -//go:nosplit -func goprintf(s string) { - vprintf(s, add(unsafe.Pointer(&s), unsafe.Sizeof(s))) -} - -// printf is only called from C code. It has the same problem as goprintf -// with strings possibly being collected from underneath. -// However, the runtime never prints dynamically allocated -// Go strings using printf. The strings it prints come from the symbol -// and type tables. +// printf is only called from C code. It has no type information for the args, +// but C stacks are ignored by the garbage collector anyway, so having +// type information would not add anything. //go:nosplit func printf(s *byte) { vprintf(gostringnocopy(s), add(unsafe.Pointer(&s), unsafe.Sizeof(s))) } -// sprintf is only called from C code. -// It has the same problem as goprintf. +// sprintf is only called from C code. It has no type information for the args, +// but C stacks are ignored by the garbage collector anyway, so having +// type information would not add anything. //go:nosplit func snprintf(dst *byte, n int32, s *byte) { buf := (*[1 << 30]byte)(unsafe.Pointer(dst))[0:n:n] |
