151 if ((a & 0xff000000U) == 0x7f000000U)
152 return LoopbackAddress;
153 if ((a & 0xf0000000U) == 0xe0000000U)
154 return MulticastAddress;
155 if ((a & 0xffff0000U) == 0xa9fe0000U)
156 return LinkLocalAddress;
157 if ((a & 0xff000000U) == 0)
158 return LocalNetAddress;
159 if ((a & 0xf0000000U) == 0xf0000000U) {
160 if (a == 0xffffffffU)
161 return BroadcastAddress;
162 return UnknownAddress;
164 if (((a & 0xff000000U) == 0x0a000000U)
165 || ((a & 0xfff00000U) == 0xac100000U)
166 || ((a & 0xffff0000U) == 0xc0a80000U))
167 return PrivateNetworkAddress;
171 return GlobalAddress;
177 quint32 high16 = qFromBigEndian(a6_32.c[0]) >> 16;
178 switch (high16 >> 8) {
180 return MulticastAddress;
182 switch (high16 & 0xffc0) {
184 return SiteLocalAddress;
187 return LinkLocalAddress;
190 return UnknownAddress;
194 return UniqueLocalAddress;
196 return GlobalAddress;
200 quint64 low64 = qFromBigEndian(a6_64.c[1]);
202 return LoopbackAddress;
203 if (low64 >> 32 == 0xffff) {
204 Q_ASSERT(quint32(low64) == 0);
205 return LocalNetAddress;
208 return GlobalAddress;
210 if (protocol == QHostAddress::UnknownNetworkLayerProtocol)
211 return UnknownAddress;
214 return LocalNetAddress;
219 static const quint8 zeroes[16] = { 0 };
230 if (address.protocol() == QHostAddress::IPv4Protocol) {
231 ip.v4 = qToBigEndian(address.toIPv4Address());
233 }
else if (address.protocol() == QHostAddress::IPv6Protocol) {
234 memcpy(ip.v6, address.toIPv6Address().c, 16);
278 if (ptr < end && memcmp(ptr + 1, zeroes, end - ptr - 1) != 0)
287 Q_ASSERT(end == 32 || end == 128);
292 quint8 bytemask = 256 - (1 << (8 - (start & 7)));
293 where[start / 8] &= bytemask;
296 memset(where + (start + 7) / 8, 0, end / 8 - (start + 7) / 8);
301 if (length == 255 || protocol == QHostAddress::AnyIPProtocol ||
302 protocol == QHostAddress::UnknownNetworkLayerProtocol) {
303 return QHostAddress();
304 }
else if (protocol == QHostAddress::IPv4Protocol) {
308 else if (length == 32)
309 a = quint32(0xffffffff);
311 a = quint32(0xffffffff) >> (32 - length) << (32 - length);
312 return QHostAddress(a);
315 memset(a6.c, 0xFF,
sizeof(a6));
316 clearBits(a6.c, length, 128);
317 return QHostAddress(a6);
658quint32 QHostAddress::toIPv4Address(
bool *ok)
const
662 *ok = d->protocol == QHostAddress::IPv4Protocol || d->protocol == QHostAddress::AnyIPProtocol
663 || (d->protocol == QHostAddress::IPv6Protocol
664 && convertToIpv4(dummy, d->a6, ConversionMode(QHostAddress::ConvertV4MappedToIPv4
665 | QHostAddress::ConvertUnspecifiedAddress)));
706QString QHostAddress::toString()
const
709 if (d->protocol == QHostAddress::IPv4Protocol
710 || d->protocol == QHostAddress::AnyIPProtocol) {
711 quint32 i = toIPv4Address();
712 QIPAddressUtils::toString(s, i);
713 }
else if (d->protocol == QHostAddress::IPv6Protocol) {
714 QIPAddressUtils::toString(s, d->a6.c);
715 if (!d->scopeId.isEmpty())
716 s += u'%' + d->scopeId;
804bool QHostAddress::isEqual(
const QHostAddress &other, ConversionMode mode)
const
809 if (d->protocol == QHostAddress::IPv4Protocol) {
810 switch (other.d->protocol) {
811 case QHostAddress::IPv4Protocol:
812 return d->a == other.d->a;
813 case QHostAddress::IPv6Protocol:
815 return convertToIpv4(a4, other.d->a6, mode) && (a4 == d->a);
816 case QHostAddress::AnyIPProtocol:
817 return (mode & QHostAddress::ConvertUnspecifiedAddress) && d->a == 0;
818 case QHostAddress::UnknownNetworkLayerProtocol:
823 if (d->protocol == QHostAddress::IPv6Protocol) {
824 switch (other.d->protocol) {
825 case QHostAddress::IPv4Protocol:
827 return convertToIpv4(a4, d->a6, mode) && (a4 == other.d->a);
828 case QHostAddress::IPv6Protocol:
829 return memcmp(&d->a6, &other.d->a6,
sizeof(Q_IPV6ADDR)) == 0;
830 case QHostAddress::AnyIPProtocol:
831 return (mode & QHostAddress::ConvertUnspecifiedAddress)
832 && (d->a6_64.c[0] == 0) && (d->a6_64.c[1] == 0);
833 case QHostAddress::UnknownNetworkLayerProtocol:
838 if ((d->protocol == QHostAddress::AnyIPProtocol)
839 && (mode & QHostAddress::ConvertUnspecifiedAddress)) {
840 switch (other.d->protocol) {
841 case QHostAddress::IPv4Protocol:
842 return other.d->a == 0;
843 case QHostAddress::IPv6Protocol:
844 return (other.d->a6_64.c[0] == 0) && (other.d->a6_64.c[1] == 0);
850 return d->protocol == other.d->protocol;
857bool QHostAddress::operator ==(SpecialAddress other)
const
859 quint32 ip4 = INADDR_ANY;
862 return d->protocol == QHostAddress::UnknownNetworkLayerProtocol;
865 ip4 = INADDR_BROADCAST;
869 ip4 = INADDR_LOOPBACK;
873 return d->protocol == QHostAddress::AnyIPProtocol;
880 if (d->protocol == QHostAddress::IPv6Protocol) {
881 quint64 second = quint8(other == LocalHostIPv6);
882 return d->a6_64.c[0] == 0 && d->a6_64.c[1] == qToBigEndian(second);
888 return d->protocol == QHostAddress::IPv4Protocol && d->a == ip4;
926bool QHostAddress::isInSubnet(
const QHostAddress &subnet,
int netmask)
const
928 if (subnet.protocol() != d->protocol || netmask < 0)
937 if (d->protocol == QHostAddress::IPv4Protocol) {
940 ip4.ip = qToBigEndian(d->a);
941 net4.ip = qToBigEndian(subnet.d->a);
944 }
else if (d->protocol == QHostAddress::IPv6Protocol) {
948 net = subnet.d->a6.c;
953 if (netmask >= 8 && memcmp(ip, net, netmask / 8) != 0)
955 if ((netmask & 7) == 0)
959 quint8 bytemask = 256 - (1 << (8 - (netmask & 7)));
960 quint8 ipbyte = ip[netmask / 8];
961 quint8 netbyte = net[netmask / 8];
962 return (ipbyte & bytemask) == (netbyte & bytemask);
1004std::pair<QHostAddress,
int> QHostAddress::parseSubnet(
const QString &subnet)
1021 const std::pair<QHostAddress,
int> invalid = std::pair(QHostAddress(), -1);
1022 if (subnet.isEmpty())
1025 qsizetype slash = subnet.indexOf(u'/');
1026 QStringView netStr(subnet);
1028 netStr.truncate(slash);
1031 bool isIpv6 = netStr.contains(u':');
1035 if (!isIpv6 && subnet.indexOf(u'.', slash + 1) != -1) {
1039 if (!mask.setAddress(subnet.mid(slash + 1)))
1041 if (!parser.setAddress(mask))
1043 netmask = parser.prefixLength();
1046 netmask = QStringView{subnet}.mid(slash + 1).toUInt(&ok);
1060 if (!net.setAddress(netStr.toString()))
1063 clearBits(net.d->a6.c, netmask, 128);
1064 return std::pair(net, netmask);
1071 auto parts = netStr.split(u'.');
1072 if (parts.isEmpty() || parts.size() > 4)
1075 if (parts.constLast().isEmpty())
1079 for (
int i = 0; i < parts.size(); ++i) {
1081 uint byteValue = parts.at(i).toUInt(&ok);
1082 if (!ok || byteValue > 255)
1088 addr <<= 8 * (4 - parts.size());
1089 if (netmask == -1) {
1090 netmask = 8 * parts.size();
1091 }
else if (netmask == 0) {
1096 }
else if (netmask != 32) {
1098 quint32 mask = quint32(0xffffffff) >> (32 - netmask) << (32 - netmask);
1102 return std::pair(QHostAddress(addr), netmask);