//===--- FixedArray.swift.gyb ---------------------------------*- swift -*-===// // // This source file is part of the Swift.org open source project // // Copyright (c) 2014 - 2017 Apple Inc. and the Swift project authors // Licensed under Apache License v2.0 with Runtime Library Exception // // See https://swift.org/LICENSE.txt for license information // See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors // //===----------------------------------------------------------------------===// // // A helper struct to provide fixed-sized array like functionality // //===----------------------------------------------------------------------===// %{ # The sizes to generate code for. sizes = [16] }% % for N in sizes: @_versioned // FIXME(sil-serialize-all) @_fixed_layout // FIXME(sil-serialize-all) internal struct _FixedArray${N} { // ABI TODO: The has assumptions about tuple layout in the ABI, namely that // they are laid out contiguously and individually addressable (i.e. strided). // @_versioned // FIXME(sil-serialize-all) internal var storage: ( // A ${N}-wide tuple of type T % for i in range(0, N-1): T, % end T ) @_versioned // FIXME(sil-serialize-all) internal static var _arraySize : Int { return ${N} } } extension _FixedArray${N} : RandomAccessCollection, MutableCollection { internal typealias Index = Int @_inlineable // FIXME(sil-serialize-all) @_versioned // FIXME(sil-serialize-all) internal var startIndex : Index { return 0 } @_inlineable // FIXME(sil-serialize-all) @_versioned // FIXME(sil-serialize-all) internal var endIndex : Index { return _FixedArray${N}._arraySize } @_versioned // FIXME(sil-serialize-all) internal var count : Int { return _FixedArray${N}._arraySize } @_inlineable // FIXME(sil-serialize-all) @_versioned // FIXME(sil-serialize-all) internal subscript(i: Index) -> T { @_versioned @inline(__always) get { var copy = storage let res: T = withUnsafeBytes(of: ©) { (rawPtr : UnsafeRawBufferPointer) -> T in let stride = MemoryLayout.stride _sanityCheck(rawPtr.count == ${N}*stride, "layout mismatch?") let bufPtr = UnsafeBufferPointer( start: rawPtr.baseAddress!.assumingMemoryBound(to: T.self), count: count) return bufPtr[i] } return res } @_versioned @inline(__always) set { withUnsafeBytes(of: &storage) { (rawPtr : UnsafeRawBufferPointer) -> () in let rawPtr = UnsafeMutableRawBufferPointer(mutating: rawPtr) let stride = MemoryLayout.stride _sanityCheck(rawPtr.count == ${N}*stride, "layout mismatch?") let bufPtr = UnsafeMutableBufferPointer( start: rawPtr.baseAddress!.assumingMemoryBound(to: T.self), count: count) bufPtr[i] = newValue } } } @_inlineable // FIXME(sil-serialize-all) @_versioned @inline(__always) internal func index(after i: Index) -> Index { return i+1 } @_inlineable // FIXME(sil-serialize-all) @_versioned @inline(__always) internal func index(before i: Index) -> Index { return i-1 } // TODO: Any customization hooks it's profitable to override, e.g. append? } extension _FixedArray${N} where T : ExpressibleByIntegerLiteral { @_inlineable // FIXME(sil-serialize-all) @_versioned // FIXME(sil-serialize-all) @inline(__always) internal init(allZeros: ()) { self.storage = ( % for i in range(0, N-1): 0, % end 0 ) } } % end