diff --git a/Sources/BinaryParsing/Parser Types/ParserSpan.swift b/Sources/BinaryParsing/Parser Types/ParserSpan.swift index a23b7bb..41ff61b 100644 --- a/Sources/BinaryParsing/Parser Types/ParserSpan.swift +++ b/Sources/BinaryParsing/Parser Types/ParserSpan.swift @@ -12,7 +12,7 @@ /// A non-owning, non-escaping view for parsing binary data. /// /// You can access a `ParserSpan` from a -public struct ParserSpan: ~Escapable, BitwiseCopyable { +public struct ParserSpan: ~Escapable, ~Copyable { @usableFromInline var _bytes: RawSpan @usableFromInline @@ -29,6 +29,14 @@ public struct ParserSpan: ~Escapable, BitwiseCopyable { self._upperBound = _bytes.byteCount } + @inlinable + @lifetime(copy other) + init(copying other: borrowing ParserSpan) { + self._bytes = other._bytes + self._lowerBound = other._lowerBound + self._upperBound = other._upperBound + } + @unsafe @inlinable @lifetime(borrow buffer) @@ -91,7 +99,7 @@ extension ParserSpan { mutating func divide(at index: Int) -> ParserSpan { precondition(index >= _lowerBound) precondition(index <= _upperBound) - var result = self + var result = ParserSpan(copying: self) result._upperBound = index self._lowerBound = index return result @@ -193,7 +201,7 @@ extension ParserSpan { _ body: (inout ParserSpan) throws(E) -> T ) throws(E) -> T { // Make a mutable copy to perform the work in `body`. - var copy = self + var copy = ParserSpan(copying: self) let result = try body(©) // `body` didn't throw, so update `self`. self = copy diff --git a/Sources/BinaryParsing/Parser Types/Seeking.swift b/Sources/BinaryParsing/Parser Types/Seeking.swift index cc52009..111b800 100644 --- a/Sources/BinaryParsing/Parser Types/Seeking.swift +++ b/Sources/BinaryParsing/Parser Types/Seeking.swift @@ -15,7 +15,7 @@ extension ParserSpan { public func seeking(toRange range: ParserRange) throws(ParsingError) -> ParserSpan { - var result = self + var result = ParserSpan(copying: self) try result.seek(toRange: range) return result } @@ -25,7 +25,7 @@ extension ParserSpan { public func seeking(toRelativeOffset offset: some FixedWidthInteger) throws(ParsingError) -> ParserSpan { - var result = self + var result = ParserSpan(copying: self) try result.seek(toRelativeOffset: offset) return result } @@ -35,7 +35,7 @@ extension ParserSpan { public func seeking(toAbsoluteOffset offset: some FixedWidthInteger) throws(ParsingError) -> ParserSpan { - var result = self + var result = ParserSpan(copying: self) try result.seek(toAbsoluteOffset: offset) return result } @@ -45,7 +45,7 @@ extension ParserSpan { public func seeking(toOffsetFromEnd offset: some FixedWidthInteger) throws(ParsingError) -> ParserSpan { - var result = self + var result = ParserSpan(copying: self) try result.seek(toOffsetFromEnd: offset) return result } diff --git a/Tests/BinaryParsingTests/SeekingTests.swift b/Tests/BinaryParsingTests/SeekingTests.swift index 15cbd4b..c494f6d 100644 --- a/Tests/BinaryParsingTests/SeekingTests.swift +++ b/Tests/BinaryParsingTests/SeekingTests.swift @@ -61,7 +61,7 @@ struct SeekingTests { // Absolute offset is always referent to original bounds var slice1 = try input.sliceSpan(byteCount: 4) - var slice2 = slice1 + var slice2 = try input.seeking(toRange: slice1.parserRange) #expect(slice1.startPosition == 2) #expect(slice1.count == 4) diff --git a/Tests/BinaryParsingTests/TestingSupport.swift b/Tests/BinaryParsingTests/TestingSupport.swift index 4d61594..2aa33fb 100644 --- a/Tests/BinaryParsingTests/TestingSupport.swift +++ b/Tests/BinaryParsingTests/TestingSupport.swift @@ -14,7 +14,7 @@ import Testing /// Returns a Boolean value indicating whether two parser spans are identical, /// representing the same subregion of the same span of memory. -func === (lhs: ParserSpan, rhs: ParserSpan) -> Bool { +func === (lhs: borrowing ParserSpan, rhs: borrowing ParserSpan) -> Bool { guard lhs.startPosition == rhs.startPosition, lhs.count == rhs.count else { return false }