使用 Swift 获取 iPhone 或 iPad 设备的 IP 地址 3
Get IPAddress of iPhone or iPad device Using Swift 3
如何使用Swift3编程语言在不使用任何第三方库的情况下检索设备的IP地址?我使用了以下代码来获取 IP 地址:
func getIPAddress() -> String? {
var address : String?
var ifaddr : UnsafeMutablePointer<ifaddrs> = nil
if getifaddrs(&ifaddr) == 0 {
var ptr = ifaddr
while ptr != nil {
defer { ptr = ptr.memory.ifa_next }
let interface = ptr.memory
let addrFamily = interface.ifa_addr.memory.sa_family
if addrFamily == UInt8(AF_INET) || addrFamily == UInt8(AF_INET6) {
if let name = String.fromCString(interface.ifa_name) where name == "en0" {
var hostname = [CChar](count: Int(NI_MAXHOST), repeatedValue: 0)
getnameinfo(interface.ifa_addr, socklen_t(interface.ifa_addr.memory.sa_len),
&hostname, socklen_t(hostname.count),
nil, socklen_t(0), NI_NUMERICHOST)
address = String.fromCString(hostname)
}
}
}
freeifaddrs(ifaddr)
}
return address
}
但是 UnsafeMutablePointer<ifaddrs>
语法不起作用。它会引发语法错误。我需要导入一个框架来帮助我吗?
在桥接头中添加 #include<ifaddrs.h>
。
这是获取 IP 地址所需的框架。
也可以参考以下link:
试试这个(不需要桥接头,它在 Playground 中有效)
//: Playground - noun: a place where people can play
import Darwin
var temp = [CChar](repeating: 0, count: 255)
enum SocketType: Int32 {
case SOCK_STREAM = 0, SOCK_DGRAM, SOCK_RAW
}
// host name
gethostname(&temp, temp.count)
// create addrinfo based on hints
// if host name is nil or "" we can connect on localhost
// if host name is specified ( like "computer.domain" ... "My-MacBook.local" )
// than localhost is not aviable.
// if port is 0, bind will assign some free port for us
var port: UInt16 = 0
let hosts = ["localhost", String(cString: temp)]
var hints = addrinfo()
hints.ai_flags = 0
hints.ai_family = PF_UNSPEC
for host in hosts {
print("\n\(host)")
print()
// retrieve the info
// getaddrinfo will allocate the memory, we are responsible to free it!
var info: UnsafeMutablePointer<addrinfo>?
defer {
if info != nil
{
freeaddrinfo(info)
}
}
var status: Int32 = getaddrinfo(host, String(port), nil, &info)
guard status == 0 else {
print(errno, String(cString: gai_strerror(errno)))
continue
}
var p = info
var i = 0
var ipFamily = ""
var ipType = ""
while p != nil {
i += 1
// use local copy of info
var _info = p!.pointee
p = _info.ai_next
switch _info.ai_family {
case PF_INET:
_info.ai_addr.withMemoryRebound(to: sockaddr_in.self, capacity: 1, { p in
inet_ntop(AF_INET, &p.pointee.sin_addr, &temp, socklen_t(temp.count))
ipFamily = "IPv4"
})
case PF_INET6:
_info.ai_addr.withMemoryRebound(to: sockaddr_in6.self, capacity: 1, { p in
inet_ntop(AF_INET6, &p.pointee.sin6_addr, &temp, socklen_t(temp.count))
ipFamily = "IPv6"
})
default:
continue
}
print(i,"\(ipFamily)\t\(String(cString: temp))", SocketType(rawValue: _info.ai_socktype)!)
}
}
它打印在我的电脑上
localhost
1 IPv6 ::1 SOCK_RAW
2 IPv6 ::1 SOCK_DGRAM
3 IPv4 127.0.0.1 SOCK_RAW
4 IPv4 127.0.0.1 SOCK_DGRAM
Ivos-MacBook-Pro.local
1 IPv6 fe80::18a2:e892:fbd7:558e SOCK_RAW
2 IPv6 fe80::18a2:e892:fbd7:558e SOCK_DGRAM
3 IPv4 172.20.10.3 SOCK_RAW
4 IPv4 172.20.10.3 SOCK_DGRAM
为了获得设备的准确 IP 地址,我做了以下事情。由于我想包含更新的代码以使用 Swift 3 获取 IP 地址,因此我在此处发布了答案。引用自
在桥接头中添加 #include<ifaddrs.h>
创建以下函数以获取 IP 地址。
func getIP()-> String? {
var address: String?
var ifaddr: UnsafeMutablePointer<ifaddrs>? = nil
if getifaddrs(&ifaddr) == 0 {
var ptr = ifaddr
while ptr != nil {
defer { ptr = ptr?.pointee.ifa_next } // memory has been renamed to pointee in swift 3 so changed memory to pointee
let interface = ptr?.pointee
let addrFamily = interface?.ifa_addr.pointee.sa_family
if addrFamily == UInt8(AF_INET) || addrFamily == UInt8(AF_INET6) {
if let name: String = String(cString: (interface?.ifa_name)!), name == "en0" { // String.fromCString() is deprecated in Swift 3. So use the following code inorder to get the exact IP Address.
var hostname = [CChar](repeating: 0, count: Int(NI_MAXHOST))
getnameinfo(interface?.ifa_addr, socklen_t((interface?.ifa_addr.pointee.sa_len)!), &hostname, socklen_t(hostname.count), nil, socklen_t(0), NI_NUMERICHOST)
address = String(cString: hostname)
}
}
}
freeifaddrs(ifaddr)
}
return address
}
为了获取IP地址,print(getIP())
验证:
-> 转到设置 -> Wi-Fi -> 单击 i 符号 -> 您可以检查您的设备 IP 地址。
输出屏幕截图:
如何使用Swift3编程语言在不使用任何第三方库的情况下检索设备的IP地址?我使用了以下代码来获取 IP 地址:
func getIPAddress() -> String? {
var address : String?
var ifaddr : UnsafeMutablePointer<ifaddrs> = nil
if getifaddrs(&ifaddr) == 0 {
var ptr = ifaddr
while ptr != nil {
defer { ptr = ptr.memory.ifa_next }
let interface = ptr.memory
let addrFamily = interface.ifa_addr.memory.sa_family
if addrFamily == UInt8(AF_INET) || addrFamily == UInt8(AF_INET6) {
if let name = String.fromCString(interface.ifa_name) where name == "en0" {
var hostname = [CChar](count: Int(NI_MAXHOST), repeatedValue: 0)
getnameinfo(interface.ifa_addr, socklen_t(interface.ifa_addr.memory.sa_len),
&hostname, socklen_t(hostname.count),
nil, socklen_t(0), NI_NUMERICHOST)
address = String.fromCString(hostname)
}
}
}
freeifaddrs(ifaddr)
}
return address
}
但是 UnsafeMutablePointer<ifaddrs>
语法不起作用。它会引发语法错误。我需要导入一个框架来帮助我吗?
在桥接头中添加 #include<ifaddrs.h>
。
这是获取 IP 地址所需的框架。
也可以参考以下link:
试试这个(不需要桥接头,它在 Playground 中有效)
//: Playground - noun: a place where people can play
import Darwin
var temp = [CChar](repeating: 0, count: 255)
enum SocketType: Int32 {
case SOCK_STREAM = 0, SOCK_DGRAM, SOCK_RAW
}
// host name
gethostname(&temp, temp.count)
// create addrinfo based on hints
// if host name is nil or "" we can connect on localhost
// if host name is specified ( like "computer.domain" ... "My-MacBook.local" )
// than localhost is not aviable.
// if port is 0, bind will assign some free port for us
var port: UInt16 = 0
let hosts = ["localhost", String(cString: temp)]
var hints = addrinfo()
hints.ai_flags = 0
hints.ai_family = PF_UNSPEC
for host in hosts {
print("\n\(host)")
print()
// retrieve the info
// getaddrinfo will allocate the memory, we are responsible to free it!
var info: UnsafeMutablePointer<addrinfo>?
defer {
if info != nil
{
freeaddrinfo(info)
}
}
var status: Int32 = getaddrinfo(host, String(port), nil, &info)
guard status == 0 else {
print(errno, String(cString: gai_strerror(errno)))
continue
}
var p = info
var i = 0
var ipFamily = ""
var ipType = ""
while p != nil {
i += 1
// use local copy of info
var _info = p!.pointee
p = _info.ai_next
switch _info.ai_family {
case PF_INET:
_info.ai_addr.withMemoryRebound(to: sockaddr_in.self, capacity: 1, { p in
inet_ntop(AF_INET, &p.pointee.sin_addr, &temp, socklen_t(temp.count))
ipFamily = "IPv4"
})
case PF_INET6:
_info.ai_addr.withMemoryRebound(to: sockaddr_in6.self, capacity: 1, { p in
inet_ntop(AF_INET6, &p.pointee.sin6_addr, &temp, socklen_t(temp.count))
ipFamily = "IPv6"
})
default:
continue
}
print(i,"\(ipFamily)\t\(String(cString: temp))", SocketType(rawValue: _info.ai_socktype)!)
}
}
它打印在我的电脑上
localhost
1 IPv6 ::1 SOCK_RAW
2 IPv6 ::1 SOCK_DGRAM
3 IPv4 127.0.0.1 SOCK_RAW
4 IPv4 127.0.0.1 SOCK_DGRAM
Ivos-MacBook-Pro.local
1 IPv6 fe80::18a2:e892:fbd7:558e SOCK_RAW
2 IPv6 fe80::18a2:e892:fbd7:558e SOCK_DGRAM
3 IPv4 172.20.10.3 SOCK_RAW
4 IPv4 172.20.10.3 SOCK_DGRAM
为了获得设备的准确 IP 地址,我做了以下事情。由于我想包含更新的代码以使用 Swift 3 获取 IP 地址,因此我在此处发布了答案。引用自
在桥接头中添加
#include<ifaddrs.h>
创建以下函数以获取 IP 地址。
func getIP()-> String? { var address: String? var ifaddr: UnsafeMutablePointer<ifaddrs>? = nil if getifaddrs(&ifaddr) == 0 { var ptr = ifaddr while ptr != nil { defer { ptr = ptr?.pointee.ifa_next } // memory has been renamed to pointee in swift 3 so changed memory to pointee let interface = ptr?.pointee let addrFamily = interface?.ifa_addr.pointee.sa_family if addrFamily == UInt8(AF_INET) || addrFamily == UInt8(AF_INET6) { if let name: String = String(cString: (interface?.ifa_name)!), name == "en0" { // String.fromCString() is deprecated in Swift 3. So use the following code inorder to get the exact IP Address. var hostname = [CChar](repeating: 0, count: Int(NI_MAXHOST)) getnameinfo(interface?.ifa_addr, socklen_t((interface?.ifa_addr.pointee.sa_len)!), &hostname, socklen_t(hostname.count), nil, socklen_t(0), NI_NUMERICHOST) address = String(cString: hostname) } } } freeifaddrs(ifaddr) } return address }
为了获取IP地址,
print(getIP())
验证:
-> 转到设置 -> Wi-Fi -> 单击 i 符号 -> 您可以检查您的设备 IP 地址。
输出屏幕截图: