1 /*
2 * Copyright (c) 2022-2024 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 "ethernet_client_fuzzer.h"
17
18 #include <cstddef>
19 #include <cstdint>
20 #include <iosfwd>
21 #include <memory>
22 #include <new>
23 #include <securec.h>
24 #include <string>
25
26 #include "netmanager_ext_test_security.h"
27 #include "refbase.h"
28 #include "singleton.h"
29
30 #include "dev_interface_state.h"
31 #define private public
32 #include "ethernet_client.h"
33 #include "ethernet_service.h"
34 #include "interface_configuration.h"
35 #include "interface_state_callback_stub.h"
36
37 namespace OHOS {
38 namespace NetManagerStandard {
39 namespace {
40 const uint8_t *g_baseFuzzData = nullptr;
41 static constexpr uint32_t CREATE_BOOL_TYPE_VALUE = 2;
42 size_t g_baseFuzzSize = 0;
43 size_t g_baseFuzzPos;
44 constexpr size_t IFACE_LEN = 5;
45 } // namespace
46
GetData()47 template <class T> T GetData()
48 {
49 T object{};
50 size_t objectSize = sizeof(object);
51 if (g_baseFuzzData == nullptr || objectSize > g_baseFuzzSize - g_baseFuzzPos) {
52 return object;
53 }
54 errno_t ret = memcpy_s(&object, objectSize, g_baseFuzzData + g_baseFuzzPos, objectSize);
55 if (ret != EOK) {
56 return {};
57 }
58 g_baseFuzzPos += objectSize;
59 return object;
60 }
61
62 class MonitorInterfaceStateCallback : public InterfaceStateCallbackStub {
63 public:
OnInterfaceAdded(const std::string & ifName)64 int32_t OnInterfaceAdded(const std::string &ifName) override
65 {
66 return 0;
67 }
68
OnInterfaceRemoved(const std::string & ifName)69 int32_t OnInterfaceRemoved(const std::string &ifName) override
70 {
71 return 0;
72 }
73
OnInterfaceChanged(const std::string & ifName,bool up)74 int32_t OnInterfaceChanged(const std::string &ifName, bool up) override
75 {
76 return 0;
77 }
78 };
79
GetStringFromData(int strlen)80 std::string GetStringFromData(int strlen)
81 {
82 char cstr[strlen];
83 cstr[strlen - 1] = '\0';
84 for (int i = 0; i < strlen - 1; i++) {
85 cstr[i] = GetData<char>();
86 }
87 std::string str(cstr);
88 return str;
89 }
90
91 static bool g_isInited = false;
92
Init()93 void Init()
94 {
95 if (!g_isInited) {
96 DelayedSingleton<EthernetService>::GetInstance()->Init();
97 g_isInited = true;
98 }
99 }
100
WriteInterfaceToken(MessageParcel & data)101 bool WriteInterfaceToken(MessageParcel &data)
102 {
103 if (!data.WriteInterfaceToken(EthernetServiceStub::GetDescriptor())) {
104 return false;
105 }
106 return true;
107 }
108
IsDataAndWriteVaild(const uint8_t * data,size_t size,MessageParcel & parcel)109 bool IsDataAndWriteVaild(const uint8_t *data, size_t size, MessageParcel &parcel)
110 {
111 if ((data == nullptr) || (size == 0)) {
112 return false;
113 }
114 NetManagerExtAccessToken token;
115 g_baseFuzzData = data;
116 g_baseFuzzSize = size;
117 g_baseFuzzPos = 0;
118
119 std::string iface = GetStringFromData(IFACE_LEN);
120 WriteInterfaceToken(parcel);
121 if (!parcel.WriteString(iface)) {
122 return false;
123 }
124
125 return true;
126 }
127
128
OnRemoteRequest(uint32_t code,MessageParcel & data)129 int32_t OnRemoteRequest(uint32_t code, MessageParcel &data)
130 {
131 if (!g_isInited) {
132 Init();
133 }
134
135 MessageParcel reply;
136 MessageOption option;
137 return DelayedSingleton<EthernetService>::GetInstance()->OnRemoteRequest(code, data, reply, option);
138 }
139
SetIfaceConfigFuzzTest(const uint8_t * data,size_t size)140 void SetIfaceConfigFuzzTest(const uint8_t *data, size_t size)
141 {
142 MessageParcel parcel;
143 if (!IsDataAndWriteVaild(data, size, parcel)) {
144 return;
145 }
146 auto ic = std::make_unique<InterfaceConfiguration>();
147 if (!ic->Marshalling(parcel)) {
148 return;
149 }
150 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_SET_IF_CFG), parcel);
151 }
152
GetIfaceConfigFuzzTest(const uint8_t * data,size_t size)153 void GetIfaceConfigFuzzTest(const uint8_t *data, size_t size)
154 {
155 if ((data == nullptr) || (size == 0)) {
156 return;
157 }
158 g_baseFuzzData = data;
159 g_baseFuzzSize = size;
160 g_baseFuzzPos = 0;
161 NetManagerExtAccessToken token;
162 MessageParcel parcel;
163 std::string iface = GetStringFromData(IFACE_LEN);
164 WriteInterfaceToken(parcel);
165 if (!parcel.WriteString(iface)) {
166 return;
167 }
168 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_GET_IF_CFG), parcel);
169 }
170
IsIfaceActiveFuzzTest(const uint8_t * data,size_t size)171 void IsIfaceActiveFuzzTest(const uint8_t *data, size_t size)
172 {
173 if ((data == nullptr) || (size == 0)) {
174 return;
175 }
176 g_baseFuzzData = data;
177 g_baseFuzzSize = size;
178 g_baseFuzzPos = 0;
179 NetManagerExtAccessToken token;
180 MessageParcel parcel;
181 std::string iface = GetStringFromData(IFACE_LEN);
182 WriteInterfaceToken(parcel);
183 if (!parcel.WriteString(iface)) {
184 return;
185 }
186 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_IS_ACTIVATE), parcel);
187 }
188
GetAllActiveIfacesFuzzTest(const uint8_t * data,size_t size)189 void GetAllActiveIfacesFuzzTest(const uint8_t *data, size_t size)
190 {
191 if ((data == nullptr) || (size == 0)) {
192 return;
193 }
194 NetManagerExtAccessToken token;
195 MessageParcel parcel;
196 WriteInterfaceToken(parcel);
197 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_GET_ACTIVATE_INTERFACE), parcel);
198 }
199
ResetFactoryFuzzTest(const uint8_t * data,size_t size)200 void ResetFactoryFuzzTest(const uint8_t *data, size_t size)
201 {
202 if ((data == nullptr) || (size == 0)) {
203 return;
204 }
205 NetManagerExtAccessToken token;
206 MessageParcel parcel;
207 WriteInterfaceToken(parcel);
208 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_RESET_FACTORY), parcel);
209 }
210
UnregisterIfacesStateChangedFuzzTest(const uint8_t * data,size_t size)211 void UnregisterIfacesStateChangedFuzzTest(const uint8_t *data, size_t size)
212 {
213 if ((data == nullptr) || (size == 0)) {
214 return;
215 }
216 NetManagerExtAccessToken token;
217 g_baseFuzzData = data;
218 g_baseFuzzSize = size;
219 g_baseFuzzPos = 0;
220 sptr<InterfaceStateCallback> interfaceCallback = new (std::nothrow) MonitorInterfaceStateCallback();
221 DelayedSingleton<EthernetClient>::GetInstance()->RegisterIfacesStateChanged(interfaceCallback);
222 DelayedSingleton<EthernetClient>::GetInstance()->UnregisterIfacesStateChanged(interfaceCallback);
223 }
224
SetInterfaceUpFuzzTest(const uint8_t * data,size_t size)225 void SetInterfaceUpFuzzTest(const uint8_t *data, size_t size)
226 {
227 MessageParcel parcel;
228 if (!IsDataAndWriteVaild(data, size, parcel)) {
229 return;
230 }
231 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_SET_INTERFACE_UP), parcel);
232 }
233
SetInterfaceDownFuzzTest(const uint8_t * data,size_t size)234 void SetInterfaceDownFuzzTest(const uint8_t *data, size_t size)
235 {
236 MessageParcel parcel;
237 if (!IsDataAndWriteVaild(data, size, parcel)) {
238 return;
239 }
240 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_SET_INTERFACE_DOWN), parcel);
241 }
242
GetInterfaceConfigFuzzTest(const uint8_t * data,size_t size)243 void GetInterfaceConfigFuzzTest(const uint8_t *data, size_t size)
244 {
245 MessageParcel parcel;
246 if (!IsDataAndWriteVaild(data, size, parcel)) {
247 return;
248 }
249 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_GET_INTERFACE_CONFIG), parcel);
250 }
251
SetInterfaceConfigFuzzTest(const uint8_t * data,size_t size)252 void SetInterfaceConfigFuzzTest(const uint8_t *data, size_t size)
253 {
254 if ((data == nullptr) || (size == 0)) {
255 return;
256 }
257 NetManagerExtAccessToken token;
258 g_baseFuzzData = data;
259 g_baseFuzzSize = size;
260 g_baseFuzzPos = 0;
261 MessageParcel parcel;
262 std::string randStr = GetStringFromData(IFACE_LEN);
263 WriteInterfaceToken(parcel);
264 if (!parcel.WriteString(randStr)) {
265 return;
266 }
267 if (!parcel.WriteString(randStr)) {
268 return;
269 }
270 if (!parcel.WriteString(randStr)) {
271 return;
272 }
273 if (!parcel.WriteString(randStr)) {
274 return;
275 }
276 if (!parcel.WriteInt32(GetData<int32_t>())) {
277 return;
278 }
279 if (!parcel.WriteInt32(1)) {
280 return;
281 }
282 if (!parcel.WriteString(randStr)) {
283 return;
284 }
285 OnRemoteRequest(static_cast<uint32_t>(EthernetInterfaceCode::CMD_SET_INTERFACE_CONFIG), parcel);
286 }
287
EthernetServiceCommonFuzzTest(const uint8_t * data,size_t size)288 void EthernetServiceCommonFuzzTest(const uint8_t *data, size_t size)
289 {
290 if ((data == nullptr) || (size == 0)) {
291 return;
292 }
293 g_baseFuzzData = data;
294 g_baseFuzzSize = size;
295 g_baseFuzzPos = 0;
296
297 auto ethernetServiceCommon = std::make_unique<EthernetServiceCommon>();
298
299 ethernetServiceCommon->ResetEthernetFactory();
300 }
301
EthernetManagementFuzzTest(const uint8_t * data,size_t size)302 void EthernetManagementFuzzTest(const uint8_t *data, size_t size)
303 {
304 if ((data == nullptr) || (size == 0)) {
305 return;
306 }
307 g_baseFuzzData = data;
308 g_baseFuzzSize = size;
309 g_baseFuzzPos = 0;
310
311 auto ethernetManagement = std::make_unique<EthernetManagement>();
312 EthernetDhcpCallback::DhcpResult dhcpResult;
313 ethernetManagement->UpdateDevInterfaceLinkInfo(dhcpResult);
314
315 std::string dev = GetStringFromData(IFACE_LEN);
316 bool up = GetData<uint32_t>() % CREATE_BOOL_TYPE_VALUE == 0;
317 ethernetManagement->UpdateInterfaceState(dev, up);
318
319 std::string iface = GetStringFromData(IFACE_LEN);
320 sptr<InterfaceConfiguration> cfg;
321 ethernetManagement->UpdateDevInterfaceCfg(iface, cfg);
322
323 sptr<InterfaceConfiguration> ifaceConfig;
324 ethernetManagement->GetDevInterfaceCfg(iface, ifaceConfig);
325
326 int32_t activeStatus = 0;
327 ethernetManagement->IsIfaceActive(iface, activeStatus);
328
329 std::vector<std::string> result;
330 ethernetManagement->GetAllActiveIfaces(result);
331
332 ethernetManagement->ResetFactory();
333 std::string devName = GetStringFromData(IFACE_LEN);
334 ethernetManagement->DevInterfaceAdd(devName);
335 ethernetManagement->DevInterfaceRemove(devName);
336 }
337
EthernetDhcpControllerFuzzTest(const uint8_t * data,size_t size)338 void EthernetDhcpControllerFuzzTest(const uint8_t *data, size_t size)
339 {
340 if ((data == nullptr) || (size == 0)) {
341 return;
342 }
343 g_baseFuzzData = data;
344 g_baseFuzzSize = size;
345 g_baseFuzzPos = 0;
346
347 auto ethernetDhcpController = std::make_unique<EthernetDhcpController>();
348
349 sptr<EthernetDhcpCallback> callback;
350 ethernetDhcpController->RegisterDhcpCallback(callback);
351
352 std::string iface = GetStringFromData(IFACE_LEN);
353 bool bIpv6 = GetData<uint32_t>() % CREATE_BOOL_TYPE_VALUE == 0;
354 ethernetDhcpController->StartClient(iface, bIpv6);
355
356 ethernetDhcpController->StopClient(iface, bIpv6);
357 }
358 } // namespace NetManagerStandard
359 } // namespace OHOS
360
361 /* Fuzzer entry point */
LLVMFuzzerTestOneInput(const uint8_t * data,size_t size)362 extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size)
363 {
364 /* Run your code on data */
365 OHOS::NetManagerStandard::SetIfaceConfigFuzzTest(data, size);
366 OHOS::NetManagerStandard::GetIfaceConfigFuzzTest(data, size);
367 OHOS::NetManagerStandard::IsIfaceActiveFuzzTest(data, size);
368 OHOS::NetManagerStandard::GetAllActiveIfacesFuzzTest(data, size);
369 OHOS::NetManagerStandard::ResetFactoryFuzzTest(data, size);
370 OHOS::NetManagerStandard::UnregisterIfacesStateChangedFuzzTest(data, size);
371 OHOS::NetManagerStandard::SetInterfaceUpFuzzTest(data, size);
372 OHOS::NetManagerStandard::SetInterfaceDownFuzzTest(data, size);
373 OHOS::NetManagerStandard::GetInterfaceConfigFuzzTest(data, size);
374 OHOS::NetManagerStandard::SetInterfaceConfigFuzzTest(data, size);
375 OHOS::NetManagerStandard::EthernetServiceCommonFuzzTest(data, size);
376 OHOS::NetManagerStandard::EthernetManagementFuzzTest(data, size);
377 OHOS::NetManagerStandard::EthernetDhcpControllerFuzzTest(data, size);
378 return 0;
379 }
380