[swift-evolution] Pitch: Improved Swift pointers

Andrew Trick atrick at apple.com
Fri Jul 14 12:47:01 CDT 2017


> On Jul 14, 2017, at 9:33 AM, Taylor Swift <kelvin13ma at gmail.com> wrote:
> 
> How would you feel about:
> 
> struct UnsafeMutableRawBufferPointer
> {
> 
> --- static func allocate(count:Int) -> UnsafeMutableRawBufferPointer
> +++ static func allocate(bytes:Int, alignedTo:Int) -> UnsafeMutableRawBufferPointer
>     func deallocate()
> +++ func bindMemory<Element>(to:Element.Type, capacity:Int)
> +++ func copy(from:UnsafeRawBufferPointer, bytes:Int)
> +++ func initializeMemory<Element>(as:Element.Type, at:Int, to:Element, count:Int)
> +++ func initializeMemory<Element>(as:Element.Type, from:UnsafeBufferPointer<Element>, count:Int)
> +++ func moveInitializeMemory<Element>(as:Element.Type, from:UnsafeMutableBufferPointer<Element>, count:Int
> }
> 
> “bytes”    = 8 bit quantities (don’t @ me we’re assuming 8 bit bytes)
> “capacity” = strided quantities, not assumed to be initialized 
> “count”    = strided quantities, assumed to be initialized
> 
> It’s also worth nothing that a lot of what the proposal tries to add to UnsafeBufferPointer is already present in UnsafeMutableRawPointer like a sizeless deallocate() and a sizeless copyBytes(from:).
> 
> Although I’m not sure what’s going on with the latter one <https://developer.apple.com/documentation/swift/unsafemutablerawbufferpointer/2635415-copybytes>…lol swiftdoc

Purely in terms of label names, what you have above is perfectly fine.

You’re going to have a problem adding the alignment constraint to buffer pointer, but that’s another topic.

-Andy

> On Fri, Jul 14, 2017 at 1:57 AM, Andrew Trick <atrick at apple.com <mailto:atrick at apple.com>> wrote:
> 
>> On Jul 13, 2017, at 10:30 PM, Taylor Swift <kelvin13ma at gmail.com <mailto:kelvin13ma at gmail.com>> wrote:
>> 
>> I’m confused I thought we were talking about the naming choices for the argument labels in those functions. I think defining and abiding by consistent meanings for `count`, `capacity`, and `bytes` is a good idea, and it’s part of what this proposal tries to accomplish. Right now half the time we use `count` to refer to “bytes” and half the time we use it to refer to “instances”. The same goes for the word “capacity”. This is all laid out in the document:
>> 
>> “““
>> Finally, the naming and design of some UnsafeMutableRawPointer members deserves to be looked at. The usage of capacity, bytes, and count as argument labels is wildly inconsistent and confusing. In copyBytes(from:count:), count refers to the number of bytes, while in initializeMemory<T>(as:at:count:to:) and initializeMemory<T>(as:from:count:), count refers to the number of strides. Meanwhile bindMemory<T>(to:capacity:) uses capacity to refer to this quantity. The always-problematic deallocate(bytes:alignedTo) method and allocate(bytes:alignedTo:) type methods use bytes to refer to byte-quantities. Adding to the confusion, UnsafeMutableRawBufferPointer offers an allocate(count:) type method (the same signature method we’re trying to add to UnsafeMutableBufferPointer), except the count in this method refers to bytes. This kind of API naming begets stride bugs and makes Swift needlessly difficult to learn.
>> ”””
>> 
>> The only convenience methods this proposal is trying to add is the functionality on the buffer pointer types. There seems to be broad support for adding this functionality as no one has really opposed that part of the proposal yet. Any other new methods like `UnsafeMutablePointer.assign(to:)` are there for API consistency.
>> 
>> This proposal also calls for getting rid of one of those “redundant initializers” :)
> 
> Since we’re not bike-shedding the specifics yet, I’ll just give you some background.
> 
> We would ultimately like APIs that allocate and initialize in one go. It’s important that the current lower-level (dangerous) APIs make a clear distinction between initialized and uninitialized memory to avoid confusing them with future (safer) APIs. `capacity` always refers to memory that may be uninitialized. I think that’s very clear and helpful.
> 
> In the context of pointers `count` should always be in strides. For raw pointers, that happens to be the same as as `bytes`.
> 
> I initially proposed copy(bytes:from:), but someone thought that `bytes` in this particular context did not properly convey the "count of bytes" as opposed to the source of the bytes. You’re right, that’s inconsistent with allocate/deallocate(bytes:), because allocateBytes(count:) would be silly. Just be aware that the inconsistency is a result of over-thinking and excessive bike shedding to the detriment of something that looks nice and is easy to remember.
> 
> I should also point out that the inconsistencies in functionality across pointer types, in terms of collection support and other convenience, is also known but was deliberately stripped from proposals as “additive”.
> 
> -Andy
> 

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.swift.org/pipermail/swift-evolution/attachments/20170714/a9518ee9/attachment.html>


More information about the swift-evolution mailing list