Thank you for the reply.
After further testing (and only implementing the bare minimum of the KMQTT library) i now only get the EPERM issue when connecting via IPv6 and i don't get the EAFNOTSUPPORT anymore. The EAFNOTSUPPORT could just have been a side effect.
I also dug deeper in the KMQTT Library and found the full POSIX usage here.
It looks like it only uses sizeof(sockaddr_in), so only the size of the IPv4 address without considering IPv6, but somehow this still works on Android.
I've tried to reproduce the issue with the following swift playground code and i also keep getting EPERM unless i use the IPv4 Address & size.
import Foundation
Thread.detachNewThread {
let socket = socket(AF_INET, SOCK_STREAM, 0)
guard socket != -1 else {
print("error creating Socket: \(errno)")
return
}
var hints = addrinfo(
ai_flags: AI_PASSIVE,
ai_family: AF_UNSPEC, // Either IPv4 or IPv6
ai_socktype: SOCK_STREAM, // TCP
ai_protocol: IPPROTO_TCP,
ai_addrlen: 0,
ai_canonname: nil,
ai_addr: nil,
ai_next: nil)
var servinfo: UnsafeMutablePointer<addrinfo>?
var name = "test.mosquitto.org".toPointer()
var port = "1883".toPointer()
let addrInfoResult = getaddrinfo(
name,
port,
nil,
&servinfo)
if addrInfoResult != 0 {
print("Error getting address: \(errno)")
return
}
let ipv4_size = UInt32(MemoryLayout<sockaddr_in>.size)
let ipv6_size = UInt32(MemoryLayout<sockaddr_in6>.size)
let dynamic_size = servinfo!.pointee.ai_addrlen
let connectResult = connect(socket, servinfo?.pointee.ai_addr, ipv6_size)
if connectResult == -1 {
print("Error connecting: \(errno)")
return
}
}
extension String {
func toPointer() -> UnsafePointer<Int8>? {
guard let data = self.data(using: String.Encoding.utf8) else { return nil }
let buffer = UnsafeMutablePointer<Int8>.allocate(capacity: data.count)
let stream = OutputStream(toBuffer: buffer, capacity: data.count)
stream.open()
data.withUnsafeBytes({ (p: UnsafePointer<Int8>) -> Void in
stream.write(p, maxLength: data.count)
})
stream.close()
return UnsafePointer<Int8>(buffer)
}
}