[SR-11315] Unsafe[Mutable][Raw]Pointer constructors are never safe when combined with implicit pointer casting. #53716
Labels
bug
A deviation from expected or documented behavior. Also: expected but undesirable behavior.
Additional Detail from JIRA
md5: d970a0bab5ab8b40872874cd7a734ff7
duplicates:
Issue Description:
Some types in the Swift standard library, such as Array or String, are capable of being implicitly promoted to pointer types. This is intended as a compatibility feature for working with C programs.
However, this implicit promotion behaviour also works for programs written in Swift: any function in Swift that takes an UnsafePointer of appropriate type can work with these stdlib types. This turns out to play poorly with the constructors of the Unsafe[Mutable][Raw]Pointer types.
There is no published rule on how long the pointer derived from the implicit promotion is valid. John's writeup on the implicit pointer conversions suggests that the answer is that the scope of the conversion is for "immediate access", but I don't think this is a well-defined duration either.
Regardless, the observed behaviour of this rule is that explicitly passing an Array or a String to the constructor of an Unsafe[Mutable][Raw]Pointer is never correct in a Swift program. The effect of doing this is to immediately produce a dangling pointer. This can be observed in the following program:
This program takes an array, creates a raw pointer from it, and passes that raw pointer to a function. The function copies bytes out of that pointer.
When compiled with {{ -sanitize=address }}, this program immediately fails:
The only way to understand the effect of this code is to observe that the pointer created from the Array is valid only for the duration of the function call for which the conversion occurred. The bug goes away if the program is changed to implicitly promote Array to UnsafeRawPointer:
This program becomes memory correct.
While the wider question of implicit pointer promotion is a difficult one to address, I think we should take action to address the fact that explicitly constructing a pointer from an Array or a String is never correct: the constructed pointer is invalid the moment it is able to be used.
I think we can address this specific problem by adding explicit constructors to the UnsafePointer types that take String or Array, and that trigger compile warnings or errors. This would eliminate an entire class of bugs to do with this use-case.
The text was updated successfully, but these errors were encountered: