diff --git a/FlyingSocks/Sources/SocketAddress.swift b/FlyingSocks/Sources/SocketAddress.swift index a5acce4..7fd2fd0 100644 --- a/FlyingSocks/Sources/SocketAddress.swift +++ b/FlyingSocks/Sources/SocketAddress.swift @@ -113,10 +113,23 @@ public extension SocketAddress where Self == sockaddr_un { extension sockaddr_storage: SocketAddress, @unchecked Swift.Sendable { public static let family = sa_family_t(AF_UNSPEC) + private var size: socklen_t { + switch Int32(family) { + case AF_INET: + socklen_t(MemoryLayout.size) + case AF_INET6: + socklen_t(MemoryLayout.size) + case AF_UNIX: + socklen_t(MemoryLayout.size) + default: + 0 + } + } + #if compiler(>=6.0) public func withSockAddr(_ body: (UnsafePointer, socklen_t) throws(E) -> R) throws(E) -> R { try withUnsafeBytes(of: self) { (p) throws(E) -> R in - try body(p.baseAddress!.assumingMemoryBound(to: sockaddr.self), socklen_t(p.count)) + try body(p.baseAddress!.assumingMemoryBound(to: sockaddr.self), size) } } @@ -128,7 +141,7 @@ extension sockaddr_storage: SocketAddress, @unchecked Swift.Sendable { #else public func withSockAddr(_ body: (UnsafePointer, socklen_t) throws -> R) rethrows -> R { try withUnsafeBytes(of: self) { p in - try body(p.baseAddress!.assumingMemoryBound(to: sockaddr.self), socklen_t(p.count)) + try body(p.baseAddress!.assumingMemoryBound(to: sockaddr.self), size) } } @@ -143,6 +156,10 @@ extension sockaddr_storage: SocketAddress, @unchecked Swift.Sendable { extension sockaddr_in: SocketAddress, @unchecked Swift.Sendable { public static let family = sa_family_t(AF_INET) + public static func make(from storage: sockaddr_storage) throws -> Self { + try makeAddress(from: storage) + } + #if compiler(>=6.0) public func withSockAddr(_ body: (UnsafePointer, socklen_t) throws(E) -> R) throws(E) -> R { try withUnsafeBytes(of: self) { (p) throws(E) -> R in @@ -162,6 +179,10 @@ extension sockaddr_in: SocketAddress, @unchecked Swift.Sendable { extension sockaddr_in6: SocketAddress, @unchecked Swift.Sendable { public static let family = sa_family_t(AF_INET6) + public static func make(from storage: sockaddr_storage) throws -> Self { + try makeAddress(from: storage) + } + #if compiler(>=6.0) public func withSockAddr(_ body: (UnsafePointer, socklen_t) throws(E) -> R) throws(E) -> R { try withUnsafeBytes(of: self) { (p) throws(E) -> R in @@ -181,6 +202,10 @@ extension sockaddr_in6: SocketAddress, @unchecked Swift.Sendable { extension sockaddr_un: SocketAddress, @unchecked Swift.Sendable { public static let family = sa_family_t(AF_UNIX) + public static func make(from storage: sockaddr_storage) throws -> Self { + try makeAddress(from: storage) + } + #if compiler(>=6.0) public func withSockAddr(_ body: (UnsafePointer, socklen_t) throws(E) -> R) throws(E) -> R { try withUnsafeBytes(of: self) { (p) throws(E) -> R in @@ -197,17 +222,12 @@ extension sockaddr_un: SocketAddress, @unchecked Swift.Sendable { } -public extension SocketAddress { - static func make(from storage: sockaddr_storage) throws -> Self { - guard self is sockaddr_storage.Type || storage.ss_family == family else { - throw SocketError.unsupportedAddress - } - var storage = storage - return withUnsafePointer(to: &storage) { - $0.withMemoryRebound(to: Self.self, capacity: 1) { - $0.pointee - } - } +package func makeAddress(from storage: sockaddr_storage) throws -> A { + guard storage.ss_family == A.family else { + throw SocketError.unsupportedAddress + } + return withUnsafeBytes(of: storage) { + $0.load(as: A.self) } }