1 /*
2 * Copyright (c) 2023 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 "interface_info.h"
17 #include <string.h>
18 #include "securec.h"
19 #include "softbus_log.h"
20 #include "softbus_error_code.h"
21 #include "protocol/wifi_direct_protocol.h"
22 #include "utils/wifi_direct_network_utils.h"
23 #include "utils/wifi_direct_ipv4_info.h"
24 #include "utils/wifi_direct_utils.h"
25 #include "utils/wifi_direct_anonymous.h"
26
27 #define LOG_LABEL "[WifiDirect] InterfaceInfo: "
28
29 #define II_TAG_DYNAMIC_MAC 0
30 #define II_TAG_INTERFACE_NAME 1
31 #define II_TAG_CONNECT_CAPABILITY 2
32 #define II_TAG_WIFI_DIRECT_ROLE 3
33 #define II_TAG_BASE_MAC 4
34 #define II_TAG_PHYSICAL_RATE 5
35 #define II_TAG_SUPPORT_BAND 6
36 #define II_TAG_CHANNEL_AND_BANDWIDTH 7
37 #define II_TAG_COEXIST_CHANNEL_LIST 8
38 #define II_TAG_HML_LINK_COUNT 9
39 #define II_TAG_ISLAND_DEVICE_COUNT 10
40 #define II_TAG_COEXIST_VAP_COUNT 11
41 #define II_TAG_IPV4 12
42 #define II_TAG_CHANNEL_5G_LIST 13
43 #define II_TAG_SSID 14
44 #define II_TAG_PORT 15
45 #define II_TAG_IS_WIDE_BAND_SUPPORT 16
46 #define II_TAG_CENTER_20M 17
47 #define II_TAG_CENTER_FREQUENCY1 18
48 #define II_TAG_CENTER_FREQUENCY2 19
49 #define II_TAG_BANDWIDTH 20
50 #define II_TAG_WIFI_CFG_INFO 21
51 #define II_TAG_IS_ENABLE 22
52 #define II_TAG_CONNECTED_DEVICE_COUNT 23
53 #define II_TAG_PSK 24
54 #define II_TAG_REUSE_COUNT 25
55 #define II_TAG_IS_AVAILABLE 26
56 #define II_TAG_COEXIST_RULE 27
57
58 IC_DECLARE_KEY_PROPERTIES(InterfaceInfo, II_KEY_MAX) = {
59 IC_KEY_PROPERTY(II_KEY_DYNAMIC_MAC, II_TAG_DYNAMIC_MAC, "DYNAMIC_MAC", STRING, MAC_ADDR_FLAG),
60 IC_KEY_PROPERTY(II_KEY_INTERFACE_NAME, II_TAG_INTERFACE_NAME, "INTERFACE_NAME", STRING, DUMP_FLAG),
61 IC_KEY_PROPERTY(II_KEY_CONNECT_CAPABILITY, II_TAG_CONNECT_CAPABILITY, "CONNECT_CAPABILITY", INT, 0),
62 IC_KEY_PROPERTY(II_KEY_WIFI_DIRECT_ROLE, II_TAG_WIFI_DIRECT_ROLE, "WIFI_DIRECT_ROLE", INT, DUMP_FLAG),
63 IC_KEY_PROPERTY(II_KEY_BASE_MAC, II_TAG_BASE_MAC, "BASE_MAC", STRING, MAC_ADDR_FLAG),
64 IC_KEY_PROPERTY(II_KEY_PHYSICAL_RATE, II_TAG_PHYSICAL_RATE, "PHYSICAL_RATE", INT, 0),
65 IC_KEY_PROPERTY(II_KEY_SUPPORT_BAND, II_TAG_SUPPORT_BAND, "SUPPORT_BAND", BYTE, 0),
66 IC_KEY_PROPERTY(II_KEY_CHANNEL_AND_BANDWIDTH, II_TAG_CHANNEL_AND_BANDWIDTH, "CHANNEL_AND_BANDWIDTH", BYTE_ARRAY, 0),
67 IC_KEY_PROPERTY(II_KEY_COEXIST_CHANNEL_LIST, II_TAG_COEXIST_CHANNEL_LIST, "COEXIST_CHANNEL_LIST", INT_ARRAY, 0),
68 IC_KEY_PROPERTY(II_KEY_HML_LINK_COUNT, II_TAG_HML_LINK_COUNT, "HML_LINK_COUNT", INT, 0),
69 IC_KEY_PROPERTY(II_KEY_ISLAND_DEVICE_COUNT, II_TAG_ISLAND_DEVICE_COUNT, "ISLAND_DEVICE_COUNT", INT, 0),
70 IC_KEY_PROPERTY(II_KEY_COEXIST_VAP_COUNT, II_TAG_COEXIST_VAP_COUNT, "COEXIST_VAP_COUNT", INT, 0),
71 IC_KEY_PROPERTY(II_KEY_IPV4, II_TAG_IPV4, "IPV4", IPV4_INFO, 0),
72 IC_KEY_PROPERTY(II_KEY_CHANNEL_5G_LIST, II_TAG_CHANNEL_5G_LIST, "CHANNEL_5G_LIST", INT_ARRAY, 0),
73 IC_KEY_PROPERTY(II_KEY_SSID, II_TAG_SSID, "SSID", STRING, 0),
74 IC_KEY_PROPERTY(II_KEY_PORT, II_TAG_PORT, "PORT", INT, 0),
75 IC_KEY_PROPERTY(II_KEY_IS_WIDE_BAND_SUPPORT, II_TAG_IS_WIDE_BAND_SUPPORT, "IS_WIDE_BAND_SUPPORT", BOOLEAN, 0),
76 IC_KEY_PROPERTY(II_KEY_CENTER_20M, II_TAG_CENTER_20M, "CENTER_20M", INT, DUMP_FLAG),
77 IC_KEY_PROPERTY(II_KEY_CENTER_FREQUENCY1, II_TAG_CENTER_FREQUENCY1, "CENTER_FREQUENCY1", INT, 0),
78 IC_KEY_PROPERTY(II_KEY_CENTER_FREQUENCY2, II_TAG_CENTER_FREQUENCY2, "CENTER_FREQUENCY2", INT, 0),
79 IC_KEY_PROPERTY(II_KEY_BANDWIDTH, II_TAG_BANDWIDTH, "BANDWIDTH", INT, 0),
80 IC_KEY_PROPERTY(II_KEY_WIFI_CFG_INFO, II_TAG_WIFI_CFG_INFO, "WIFI_CFG_INFO", BYTE_ARRAY, 0),
81 IC_KEY_PROPERTY(II_KEY_IS_ENABLE, II_TAG_IS_ENABLE, "IS_ENABLE", BOOLEAN, DUMP_FLAG),
82 IC_KEY_PROPERTY(II_KEY_CONNECTED_DEVICE_COUNT, II_TAG_CONNECTED_DEVICE_COUNT, "CONNECTED_DEVICE_COUNT", INT,
83 DUMP_FLAG),
84 IC_KEY_PROPERTY(II_KEY_PSK, II_TAG_PSK, "PSK", STRING, 0),
85 IC_KEY_PROPERTY(II_KEY_REUSE_COUNT, II_TAG_REUSE_COUNT, "REUSE_COUNT", INT, DUMP_FLAG),
86 IC_KEY_PROPERTY(II_KEY_IS_AVAILABLE, II_TAG_IS_AVAILABLE, "IS_AVAILABLE", BOOLEAN, 0),
87 IC_KEY_PROPERTY(II_KEY_COEXIST_RULE, II_TAG_COEXIST_RULE, "COEXIST_RULE", COEXIST_SET, 0),
88 };
89
90 /* private method forward declare */
91 static size_t GetKeyFromKeyProperty(struct InfoContainerKeyProperty *keyProperty);
92 static bool MarshallingMacAddress(struct InterfaceInfo *self, struct WifiDirectProtocol *protocol,
93 enum InterfaceInfoKey key);
94 static bool UnmarshallingMacAddress(struct InterfaceInfo *self, enum InterfaceInfoKey key, uint8_t *data, size_t size);
95
96 /* public interface */
GetKeySize(void)97 static size_t GetKeySize(void)
98 {
99 return II_KEY_MAX;
100 }
101
GetContainerName(void)102 static const char* GetContainerName(void)
103 {
104 return "InterfaceInfo";
105 }
106
MarshallingString(struct WifiDirectProtocol * protocol,struct InfoContainerKeyProperty * keyProperty,size_t key,uint8_t * value,size_t size)107 static bool MarshallingString(struct WifiDirectProtocol *protocol,
108 struct InfoContainerKeyProperty *keyProperty, size_t key, uint8_t *value, size_t size)
109 {
110 bool ret = false;
111 if (key == II_KEY_DYNAMIC_MAC || key == II_KEY_BASE_MAC) {
112 uint8_t mac[MAC_ADDR_ARRAY_SIZE];
113 size_t macSize = sizeof(mac);
114 if (GetWifiDirectNetWorkUtils()->macStringToArray((char *)value, mac, &macSize) != SOFTBUS_OK) {
115 CLOGE(LOG_LABEL "mac string to bytes failed");
116 return false;
117 }
118 ret = protocol->writeData(protocol, keyProperty, mac, macSize);
119 } else {
120 ret = protocol->writeData(protocol, keyProperty, value, size >= 1 ? size - 1 : 0);
121 }
122
123 return ret;
124 }
125
UnmarshallingString(struct InterfaceInfo * self,size_t key,uint8_t * data,size_t size)126 static bool UnmarshallingString(struct InterfaceInfo *self, size_t key, uint8_t *data, size_t size)
127 {
128 if (key == II_KEY_DYNAMIC_MAC || key == II_KEY_BASE_MAC) {
129 char macStr[MAC_ADDR_STR_LEN];
130 if (GetWifiDirectNetWorkUtils()->macArrayToString(data, size, macStr, sizeof(macStr)) != SOFTBUS_OK) {
131 CLOGE(LOG_LABEL "mac bytes to string failed");
132 return false;
133 }
134 self->putString(self, key, macStr);
135 } else {
136 char *string = SoftBusCalloc(size + 1);
137 CONN_CHECK_AND_RETURN_RET_LOG(string, false, LOG_LABEL "alloc failed");
138 if (memcpy_s(string, size + 1, data, size) != EOK) {
139 CLOGE(LOG_LABEL "memcpy data failed");
140 SoftBusFree(string);
141 return false;
142 }
143 self->putString(self, key, string);
144 SoftBusFree(string);
145 }
146
147 return true;
148 }
149
Marshalling(struct InterfaceInfo * self,struct WifiDirectProtocol * protocol)150 static bool Marshalling(struct InterfaceInfo *self, struct WifiDirectProtocol *protocol)
151 {
152 enum WifiDirectProtocolType protocolType = protocol->getType();
153
154 for (size_t key = 0; key < II_KEY_MAX; key++) {
155 size_t size = 0;
156 uint8_t *value = self->get(self, key, &size, NULL);
157 if (!value || !size) {
158 continue;
159 }
160
161 bool ret = false;
162 struct InfoContainerKeyProperty *keyProperty = self->keyProperties + key;
163 if (protocolType == WIFI_DIRECT_PROTOCOL_TLV && (key == II_KEY_BASE_MAC || key == II_KEY_DYNAMIC_MAC)) {
164 ret = MarshallingMacAddress(self, protocol, key);
165 CONN_CHECK_AND_RETURN_RET_LOG(ret, false, LOG_LABEL "mac address marshalling failed, key=%d", key);
166 continue;
167 }
168
169 switch (keyProperty->type) {
170 case BOOLEAN: {
171 uint8_t boolValue = (uint8_t)!!*(bool *)value;
172 ret = protocol->writeData(protocol, keyProperty, &boolValue, 1);
173 break;
174 }
175 case INT:{
176 uint8_t bytes[sizeof(uint32_t)] = {0};
177 GetWifiDirectUtils()->intToBytes(*(uint32_t*)value, sizeof(uint32_t), bytes, sizeof(bytes));
178 ret = protocol->writeData(protocol, keyProperty, bytes, sizeof(bytes));
179 }
180 break;
181 case BYTE:
182 case INT_ARRAY:
183 case BYTE_ARRAY:
184 ret = protocol->writeData(protocol, keyProperty, value, size);
185 break;
186 case STRING:
187 ret = MarshallingString(protocol, keyProperty, key, value, size);
188 break;
189 default:
190 ret = true;
191 break;
192 }
193
194 CONN_CHECK_AND_RETURN_RET_LOG(ret, false, LOG_LABEL "marshalling failed, key=%d", key);
195 }
196
197 return true;
198 }
199
Unmarshalling(struct InterfaceInfo * self,struct WifiDirectProtocol * protocol)200 static bool Unmarshalling(struct InterfaceInfo *self, struct WifiDirectProtocol *protocol)
201 {
202 size_t size = 0;
203 uint8_t *data = NULL;
204 struct InfoContainerKeyProperty keyProperty;
205 enum WifiDirectProtocolType protocolType = protocol->getType();
206
207 while (protocol->readData(protocol, &keyProperty, &data, &size)) {
208 bool ret = false;
209 enum InterfaceInfoKey key = GetKeyFromKeyProperty(&keyProperty);
210 CONN_CHECK_AND_RETURN_RET_LOG(key < II_KEY_MAX, false, LOG_LABEL "key out of range, tag=%d", keyProperty.tag);
211 if (!data || !size) {
212 continue;
213 }
214
215 if (protocolType == WIFI_DIRECT_PROTOCOL_TLV && (key == II_KEY_BASE_MAC || key == II_KEY_DYNAMIC_MAC)) {
216 ret = UnmarshallingMacAddress(self, key, data, size);
217 CONN_CHECK_AND_RETURN_RET_LOG(ret, false, LOG_LABEL "mac address unmarshalling failed key=%d", key);
218 continue;
219 }
220
221 switch (keyProperty.type) {
222 case BOOLEAN:
223 self->putBoolean(self, key, (bool)data[0]);
224 ret = true;
225 break;
226 case INT:
227 self->putInt(self, key, (int32_t)GetWifiDirectUtils()->bytesToInt(data, size));
228 ret = true;
229 break;
230 case BYTE:
231 case INT_ARRAY:
232 case BYTE_ARRAY:
233 self->putRawData(self, key, data, size);
234 ret = true;
235 break;
236 case STRING:
237 ret = UnmarshallingString(self, key, data, size);
238 break;
239 default:
240 continue;
241 }
242
243 data = NULL;
244 size = 0;
245 CONN_CHECK_AND_RETURN_RET_LOG(ret, false, LOG_LABEL "unmarshalling failed key=%d", key);
246 }
247
248 return true;
249 }
250
GetName(struct InterfaceInfo * self)251 static char* GetName(struct InterfaceInfo *self)
252 {
253 return self->getString(self, II_KEY_INTERFACE_NAME, "");
254 }
255
PutName(struct InterfaceInfo * self,const char * name)256 static void PutName(struct InterfaceInfo *self, const char *name)
257 {
258 self->putString(self, II_KEY_INTERFACE_NAME, name);
259 }
260
GetIpString(struct InterfaceInfo * self,char * ipString,int32_t ipStringSize)261 static int32_t GetIpString(struct InterfaceInfo *self, char *ipString, int32_t ipStringSize)
262 {
263 struct WifiDirectIpv4Info *ipv4 = self->getRawData(self, II_KEY_IPV4, NULL, NULL);
264 return WifiDirectIpv4ToString(ipv4, ipString, ipStringSize);
265 }
266
PutIpString(struct InterfaceInfo * self,const char * ipString)267 static void PutIpString(struct InterfaceInfo *self, const char *ipString)
268 {
269 struct WifiDirectIpv4Info ipv4;
270 int32_t ret = WifiDirectIpStringToIpv4(ipString, &ipv4);
271 CONN_CHECK_AND_RETURN_LOG(ret == SOFTBUS_OK, "ip to ipv4 failed");
272 self->putRawData(self, II_KEY_IPV4, &ipv4, sizeof(ipv4));
273 }
274
GetP2pGroupConfig(struct InterfaceInfo * self,char * buffer,size_t bufferSize)275 static int32_t GetP2pGroupConfig(struct InterfaceInfo *self, char *buffer, size_t bufferSize)
276 {
277 int32_t ret = sprintf_s(buffer, bufferSize, "%s\n%s\n%s\n%d",
278 self->getString(self, II_KEY_SSID, ""),
279 self->getString(self, II_KEY_DYNAMIC_MAC, ""),
280 self->getString(self, II_KEY_PSK, ""),
281 self->getInt(self, II_KEY_CENTER_20M, 0));
282 if (ret < 0) {
283 CLOGE(LOG_LABEL "format group config failed");
284 return SOFTBUS_ERR;
285 }
286
287 return SOFTBUS_OK;
288 }
289
SetP2pGroupConfig(struct InterfaceInfo * self,char * groupConfig)290 static int32_t SetP2pGroupConfig(struct InterfaceInfo *self, char *groupConfig)
291 {
292 char *configs[P2P_GROUP_CONFIG_INDEX_MAX] = {0};
293 size_t configsSize = P2P_GROUP_CONFIG_INDEX_MAX;
294 int32_t ret = GetWifiDirectNetWorkUtils()->splitString(groupConfig, "\n", configs, &configsSize);
295 CONN_CHECK_AND_RETURN_RET_LOG(ret == SOFTBUS_OK && configsSize > P2P_GROUP_CONFIG_INDEX_FREQ,
296 SOFTBUS_ERR, "split group config failed");
297
298 self->putString(self, II_KEY_SSID, configs[P2P_GROUP_CONFIG_INDEX_SSID]);
299 if (!self->get(self, II_KEY_DYNAMIC_MAC, NULL, NULL)) {
300 self->putString(self, II_KEY_DYNAMIC_MAC, configs[P2P_GROUP_CONFIG_INDEX_BSSID]);
301 }
302 self->putString(self, II_KEY_PSK, configs[P2P_GROUP_CONFIG_INDEX_SHARE_KEY]);
303 self->putInt(self, II_KEY_CENTER_20M, atoi(configs[P2P_GROUP_CONFIG_INDEX_FREQ]));
304
305 return SOFTBUS_OK;
306 }
307
IncreaseRefCount(struct InterfaceInfo * self)308 static void IncreaseRefCount(struct InterfaceInfo *self)
309 {
310 int32_t *count = self->get(self, II_KEY_REUSE_COUNT, NULL, NULL);
311 if (count) {
312 ++*count;
313 CLOGI(LOG_LABEL "reuseCount=%d", *count);
314 } else {
315 CLOGI(LOG_LABEL "Count is null");
316 }
317 }
318
DecreaseRefCount(struct InterfaceInfo * self)319 static void DecreaseRefCount(struct InterfaceInfo *self)
320 {
321 int32_t *count = self->get(self, II_KEY_REUSE_COUNT, NULL, NULL);
322 if (count) {
323 --*count;
324 CLOGI(LOG_LABEL "reuseCount=%d", *count);
325 } else {
326 CLOGI(LOG_LABEL "Count is null");
327 }
328 }
329
330 /* private method implement */
GetKeyFromKeyProperty(struct InfoContainerKeyProperty * keyProperty)331 static size_t GetKeyFromKeyProperty(struct InfoContainerKeyProperty *keyProperty)
332 {
333 struct InfoContainerKeyProperty *predefineKeyProperty = NULL;
334 for (size_t key = 0; key < II_KEY_MAX; key++) {
335 predefineKeyProperty = InterfaceInfoKeyProperties + key;
336 if ((keyProperty->content && strcmp(keyProperty->content, predefineKeyProperty->content) == 0) ||
337 (keyProperty->tag == predefineKeyProperty->tag)) {
338 *keyProperty = *predefineKeyProperty;
339 return key;
340 }
341 }
342
343 return II_KEY_MAX;
344 }
345
MarshallingMacAddress(struct InterfaceInfo * self,struct WifiDirectProtocol * protocol,enum InterfaceInfoKey key)346 static bool MarshallingMacAddress(struct InterfaceInfo *self, struct WifiDirectProtocol *protocol,
347 enum InterfaceInfoKey key)
348 {
349 char *addressString = self->getString(self, key, "");
350 if (strlen(addressString) == 0) {
351 CLOGI(LOG_LABEL "empty address string");
352 return true;
353 }
354
355 size_t addressSize = MAC_ADDR_ARRAY_SIZE;
356 uint8_t address[MAC_ADDR_ARRAY_SIZE];
357 int32_t ret = GetWifiDirectNetWorkUtils()->macStringToArray(addressString, address, &addressSize);
358 CONN_CHECK_AND_RETURN_RET_LOG(ret == SOFTBUS_OK, false, LOG_LABEL "mac string to array failed");
359
360 protocol->writeData(protocol, &InterfaceInfoKeyProperties[key], address, addressSize);
361 return true;
362 }
363
UnmarshallingMacAddress(struct InterfaceInfo * self,enum InterfaceInfoKey key,uint8_t * data,size_t size)364 static bool UnmarshallingMacAddress(struct InterfaceInfo *self, enum InterfaceInfoKey key, uint8_t *data, size_t size)
365 {
366 CONN_CHECK_AND_RETURN_RET_LOG(size == MAC_ADDR_ARRAY_SIZE, false, LOG_LABEL "size=%d is invalid", size);
367 char address[MAC_ADDR_STR_LEN] = {0};
368 int32_t ret = GetWifiDirectNetWorkUtils()->macArrayToString(data, size, address, sizeof(address));
369 CONN_CHECK_AND_RETURN_RET_LOG(ret == SOFTBUS_OK, false, LOG_LABEL "mac array to string failed");
370 self->putString(self, key, address);
371 return true;
372 }
373
374 /* constructor and destructor */
InterfaceInfoConstructor(struct InterfaceInfo * self)375 void InterfaceInfoConstructor(struct InterfaceInfo* self)
376 {
377 InfoContainerConstructor((struct InfoContainer *)self, InterfaceInfoKeyProperties, II_KEY_MAX);
378
379 self->getKeySize = GetKeySize;
380 self->getContainerName = GetContainerName;
381 self->marshalling = Marshalling;
382 self->unmarshalling = Unmarshalling;
383 self->destructor = InterfaceInfoDestructor;
384
385 self->getName = GetName;
386 self->putName = PutName;
387 self->getIpString = GetIpString;
388 self->putIpString = PutIpString;
389 self->getP2pGroupConfig = GetP2pGroupConfig;
390 self->setP2pGroupConfig = SetP2pGroupConfig;
391 self->increaseRefCount = IncreaseRefCount;
392 self->decreaseRefCount = DecreaseRefCount;
393
394 ListInit(&self->node);
395 }
396
InterfaceInfoConstructorWithName(struct InterfaceInfo * self,const char * name)397 void InterfaceInfoConstructorWithName(struct InterfaceInfo* self, const char *name)
398 {
399 InterfaceInfoConstructor(self);
400 self->putName(self, name);
401 }
402
InterfaceInfoDestructor(struct InterfaceInfo * self)403 void InterfaceInfoDestructor(struct InterfaceInfo* self)
404 {
405 InfoContainerDestructor((struct InfoContainer *)self, II_KEY_MAX);
406 }
407
408 /* new and delete */
InterfaceInfoNew(void)409 struct InterfaceInfo* InterfaceInfoNew(void)
410 {
411 struct InterfaceInfo *self = (struct InterfaceInfo *)SoftBusCalloc(sizeof(*self));
412 if (self) {
413 InterfaceInfoConstructor(self);
414 }
415
416 return self;
417 }
418
InterfaceInfoDelete(struct InterfaceInfo * self)419 void InterfaceInfoDelete(struct InterfaceInfo* self)
420 {
421 InterfaceInfoDestructor(self);
422 SoftBusFree(self);
423 }
424
InterfaceInfoNewArray(size_t size)425 struct InterfaceInfo* InterfaceInfoNewArray(size_t size)
426 {
427 struct InterfaceInfo *self = (struct InterfaceInfo *)SoftBusCalloc(sizeof(*self) * size);
428 if (self) {
429 for (size_t i = 0; i < size; i++) {
430 InterfaceInfoConstructor(self + i);
431 }
432 }
433
434 return self;
435 }
436
InterfaceInfoDeleteArray(struct InterfaceInfo * self,size_t size)437 void InterfaceInfoDeleteArray(struct InterfaceInfo *self, size_t size)
438 {
439 for (size_t i = 0; i < size; i++) {
440 InterfaceInfoDestructor(self + i);
441 }
442 SoftBusFree(self);
443 }