-
Notifications
You must be signed in to change notification settings - Fork 18.4k
Description
The cgo pointer passing rules (and previously the Pinner
documentation) states something like:
[Only pointers that are] the result of calling new, taking the address of a composite literal, or taking the address of a local variable[ may be passed to C and/or pinned].
This wasn't really accurate in practice and also placed restrictions on the API that made it harder to allow new cases in the future (see #62356 and #63768).
Even still, the Pinner
API explicitly rejects non-pointer types today, but there are ways to work around that for some common use-cases like strings and slices:
- For slices, simply passing
&s[0]
works. - For strings, passing
unsafe.StringData(s)
works.
While strings require unsafe, it's particularly surprising that slice elements just work given the documentation. Also, given that Go strings can already be passed as _GoString_
to C functions, it makes sense that they should be included as well.
I propose allowing both strings and slices as valid arguments to Pinner
. The semantics are clear: pin the underlying memory for the string or the slice backing store. Callers are also able to pin any pointers inside the slice backing store (but Pinner
will not do this for them automatically). We should make clear that C code is only allowed to access and manipulate the part of the slice backing store that has been pinned; going out-of-bounds on the slice passed to C is not OK.
Metadata
Metadata
Assignees
Labels
Type
Projects
Status