1 /*
2 * Copyright (C) 2021-2022 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "ipv4_address.h"
17 #include <cstdio>
18 #include <string>
19 #include <arpa/inet.h>
20 #include <sys/socket.h>
21 #include "wifi_log.h"
22
23 #undef LOG_TAG
24 #define LOG_TAG "OHWIFI_UTIL_Ipv4Address"
25
26 namespace OHOS {
27 namespace Wifi {
28 const int MAX_IPV4_PREFIX_LENGTH = 32;
29 const int MAX_IPV4_STRING_LENGTH = 64;
30 const Ipv4Address Ipv4Address::invalidInetAddress("255.255.255.255", MAX_IPV4_PREFIX_LENGTH);
31 const Ipv4Address Ipv4Address::defaultInetAddress("192.168.49.1", MAX_IPV4_PREFIX_LENGTH);
IsValidIPv4(const std::string & ipv4)32 bool Ipv4Address::IsValidIPv4(const std::string &ipv4)
33 {
34 struct in_addr ipv4Addr = {INADDR_ANY};
35 if (inet_pton(AF_INET, ipv4.c_str(), static_cast<void*>(&ipv4Addr)) != 1 ||
36 ipv4 == invalidInetAddress.GetAddressWithString()) {
37 return false;
38 } else {
39 return true;
40 }
41 }
42
Create(const std::string & ipv4,size_t prefixLength)43 Ipv4Address Ipv4Address::Create(const std::string &ipv4, size_t prefixLength)
44 {
45 if (!IsValidIPv4(ipv4) || prefixLength > MAX_IPV4_PREFIX_LENGTH - 1) {
46 return invalidInetAddress;
47 }
48 return Ipv4Address(ipv4, prefixLength);
49 }
50
Create(const std::string & ipv4,const std::string & mask)51 Ipv4Address Ipv4Address::Create(const std::string &ipv4, const std::string &mask)
52 {
53 size_t prefixLength = 0;
54 struct in_addr maskAddr = {INADDR_ANY};
55 if ((inet_aton(mask.c_str(), &maskAddr) != 1) || (!IsValidIPv4(ipv4))) {
56 return invalidInetAddress;
57 }
58 for (int i = 0; i < MAX_MASK_LENGTH; i++) {
59 if (maskAddr.s_addr != 0) {
60 maskAddr.s_addr = maskAddr.s_addr >> 1;
61 ++prefixLength;
62 }
63 }
64 return Ipv4Address(ipv4, prefixLength);
65 }
66
Create(const in_addr & ipv4,const in_addr & mask)67 Ipv4Address Ipv4Address::Create(const in_addr &ipv4, const in_addr &mask)
68 {
69 size_t prefixLength = 0;
70 struct in_addr maskAddr = mask;
71 for (int i = 0; i < MAX_MASK_LENGTH; i++) {
72 if (maskAddr.s_addr != 0) {
73 maskAddr.s_addr = maskAddr.s_addr >> 1;
74 ++prefixLength;
75 }
76 }
77 char ipStr[MAX_IPV4_STRING_LENGTH] = {0};
78 if (inet_ntop(AF_INET, &ipv4, ipStr, sizeof(ipStr)) == nullptr) {
79 return invalidInetAddress;
80 }
81 return Ipv4Address(ipStr, prefixLength);
82 }
83
Ipv4Address(const std::string & ipv4,size_t prefixLength)84 Ipv4Address::Ipv4Address(const std::string &ipv4, size_t prefixLength)
85 : BaseAddress(ipv4, prefixLength, FamilyType::FAMILY_INET)
86 {}
87
IsValid() const88 bool Ipv4Address::IsValid() const
89 {
90 return IsValidIPv4(GetAddressWithString());
91 }
92
GetAddressWithInet() const93 in_addr Ipv4Address::GetAddressWithInet() const
94 {
95 struct in_addr ipv4Addr = {INADDR_ANY};
96 if (inet_aton(GetAddressWithString().c_str(), &ipv4Addr) == 0) {
97 LOGI("inet_aton error");
98 }
99 return ipv4Addr;
100 }
101
GetMaskWithString() const102 std::string Ipv4Address::GetMaskWithString() const
103 {
104 char ipStr[MAX_IPV4_STRING_LENGTH] = {0};
105 in_addr ipAddr = GetMaskWithInet();
106 if (inet_ntop(AF_INET, &ipAddr, ipStr, sizeof(ipStr)) == nullptr) {
107 return "";
108 }
109 return std::string(ipStr);
110 }
111
GetMaskWithInet() const112 in_addr Ipv4Address::GetMaskWithInet() const
113 {
114 struct in_addr mask4Addr = {INADDR_ANY};
115 size_t num = GetAddressPrefixLength();
116 size_t i = 0xffffffff;
117 i = i >> (MAX_MASK_LENGTH - num);
118 mask4Addr.s_addr = i;
119 return mask4Addr;
120 }
121
GetNetworkAddressWithString() const122 std::string Ipv4Address::GetNetworkAddressWithString() const
123 {
124 char ipStr[MAX_IPV4_STRING_LENGTH] = {0};
125 in_addr ipAddr = GetNetworkAddressWithInet();
126 if (inet_ntop(AF_INET, &ipAddr, ipStr, sizeof(ipStr)) == nullptr) {
127 return "";
128 }
129 return std::string(ipStr);
130 }
131
GetNetworkAddressWithInet() const132 in_addr Ipv4Address::GetNetworkAddressWithInet() const
133 {
134 struct in_addr networkAddress = {INADDR_ANY};
135 networkAddress.s_addr = GetMaskWithInet().s_addr & GetAddressWithInet().s_addr;
136 return networkAddress;
137 }
138
GetHostAddressWithString() const139 std::string Ipv4Address::GetHostAddressWithString() const
140 {
141 char ipStr[MAX_IPV4_STRING_LENGTH] = {0};
142 in_addr ipAddr = GetHostAddressWithInet();
143 if (inet_ntop(AF_INET, &ipAddr, ipStr, sizeof(ipStr)) == nullptr) {
144 return "";
145 }
146 return std::string(ipStr);
147 }
148
GetHostAddressWithInet() const149 in_addr Ipv4Address::GetHostAddressWithInet() const
150 {
151 struct in_addr hostAddress = {INADDR_ANY};
152 hostAddress.s_addr = (~(GetMaskWithInet().s_addr)) & GetAddressWithInet().s_addr;
153 return hostAddress;
154 }
155
GetNetwork() const156 std::string Ipv4Address::GetNetwork() const
157 {
158 std::string network = GetAddressWithString() + "/" + std::to_string(GetAddressPrefixLength());
159 return network;
160 }
161 } // namespace Wifi
162 } // namespace OHOS
163