Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[SR-13876] Can't use read/modify coroutines with ManagedBufferPointer #56274

Open
lilyball mannequin opened this issue Nov 19, 2020 · 2 comments
Open

[SR-13876] Can't use read/modify coroutines with ManagedBufferPointer #56274

lilyball mannequin opened this issue Nov 19, 2020 · 2 comments
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior. standard library Area: Standard library umbrella

Comments

@lilyball
Copy link
Mannequin

lilyball mannequin commented Nov 19, 2020

Previous ID SR-13876
Radar rdar://problem/71590289
Original Reporter @lilyball
Type Bug
Environment

Apple Swift version 5.3.1 (swiftlang-1200.0.41 clang-1200.0.32.8)
Target: x86_64-apple-darwin19.6.0

Additional Detail from JIRA
Votes 0
Component/s Standard Library
Labels Bug
Assignee None
Priority Medium

md5: 0c18920adc9998bc7d15e5bef9a86363

Issue Description:

ManagedBuffer and ManagedBufferPointer restrict access to their elements via methods that take closures. I assume this is done to prevent the caller from having to worry about the buffer lifetime.

The problem is this means I can't use read/modify coroutines to yield elements (e.g. as the subscript for a custom collection type). I know they're not stable yet (at least in Swift 5.3) but I'd really like to use them anyway because of performance concerns. And right now my only choice is to have the coroutine move the element onto the stack, yield it, and then move it back into the managed buffer. Since my collection type is generic this means I have no way to make an informed choice as to whether moving the element back and forth is better or worse than just using get/set.

I don't know how the coroutines are implemented, but I assume it's not feasible to make yield work from inside a nested closure. Given that, I think the best solution here is to just give me a way to address elements of a ManagedBuffer or ManagedBufferPointer directly. This could look something like

extension ManagedBufferPointer {
    subscript(unsafeElementAt offset: Int) -> Element {
        _read {
            yield _elementPointer[offset]
        }
        nonmutating _modify {
            yield &_elementPointer[offset]
        }
    }
}

This way I can then yield &buffer[unsafeElementAt: offset] in my own _modify and I won't run into this issue. It would also simplify the get/set case because it turns return buffer.withUnsafeMutablePointerToElements({ $0[offset] }) into return buffer[unsafeElementAt: offset].

@typesanitizer
Copy link

@swift-ci create

@lorentey
Copy link
Member

I agree 100% – exposing an unsafe subscript is most likely the right thing to do here.

@swift-ci swift-ci transferred this issue from apple/swift-issues Apr 25, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior. standard library Area: Standard library umbrella
Projects
None yet
Development

No branches or pull requests

2 participants