1 /*
2 * Copyright (c) 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 "net_stats_database_helper.h"
17
18 #include <cstdlib>
19 #include <filesystem>
20
21 #include "net_manager_constants.h"
22 #include "net_mgr_log_wrapper.h"
23 #include "net_stats_constants.h"
24 #include "net_stats_database_defines.h"
25 #include "net_stats_info.h"
26
27 namespace OHOS {
28 namespace NetManagerStandard {
29 using namespace NetStatsDatabaseDefines;
30
31 constexpr const char* SELECT_FROM = "SELECT * FROM ";
32 constexpr const char* DELETE_FROM = "DELETE FROM ";
33 constexpr const char* UPDATE = "UPDATE ";
34 constexpr const char* ALTER_TABLE = "ALTER TABLE ";
35 constexpr const char* DATA_MORE_THAN = " AND t.Date >= ?";
36 constexpr const char* DATA_LESS_THAN = " AND t.Date <= ?";
37 constexpr const char* INSERT_OR_REPLACE_INTO = "INSERT OR REPLACE INTO ";
38 constexpr const char* SET_FLAG = " SET Flag = ";
39 constexpr const char* SET_USERID = " SET UserId = ";
40 namespace {
__anone4d128c40202(void *notUsed, int argc, char **argv, char **colName) 41 NetStatsDatabaseHelper::SqlCallback sqlCallback = [](void *notUsed, int argc, char **argv, char **colName) {
42 std::string data;
43 for (int i = 0; i < argc; i++) {
44 data.append(colName[i]).append(" = ").append(argv[i] ? argv[i] : "nullptr\n");
45 }
46 NETMGR_LOG_D("Recv data: %{public}s", data.c_str());
47 return 0;
48 };
49
CheckFilePath(const std::string & fileName)50 bool CheckFilePath(const std::string &fileName)
51 {
52 char tmpPath[PATH_MAX] = {0};
53 const auto pos = fileName.find_last_of('/');
54 const auto dir = fileName.substr(0, pos);
55 if (!realpath(dir.c_str(), tmpPath)) {
56 NETMGR_LOG_E("Get realPath failed error: %{public}d, %{public}s", errno, strerror(errno));
57 return false;
58 }
59 if (strcmp(tmpPath, dir.c_str()) != 0) {
60 NETMGR_LOG_E("file name is illegal fileName: %{public}s, tmpPath: %{public}s", fileName.c_str(), tmpPath);
61 return false;
62 }
63 return true;
64 }
65 } // namespace
66
67 ffrt::mutex NetStatsDatabaseHelper::sqliteMutex_;
68
NetStatsDatabaseHelper(const std::string & path)69 NetStatsDatabaseHelper::NetStatsDatabaseHelper(const std::string &path)
70 {
71 if (!CheckFilePath(path)) {
72 return;
73 }
74 Open(path);
75 path_ = path;
76 isDisplayTrafficAncoList_ = CommonUtils::IsNeedDisplayTrafficAncoList();
77 }
78
~NetStatsDatabaseHelper()79 NetStatsDatabaseHelper::~NetStatsDatabaseHelper()
80 {
81 Close();
82 sqlite_ = nullptr;
83 }
84
ExecSql(const std::string & sql,void * recv,SqlCallback callback)85 int32_t NetStatsDatabaseHelper::ExecSql(const std::string &sql, void *recv, SqlCallback callback)
86 {
87 char *errMsg = nullptr;
88 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
89 int32_t ret = sqlite3_exec(sqlite_, sql.c_str(), callback, recv, &errMsg);
90 lock.unlock();
91 NETMGR_LOG_D("EXEC SQL : %{public}s", sql.c_str());
92 if (errMsg != nullptr) {
93 NETMGR_LOG_E("Exec sql failed err:%{public}s, path: %{public}s", errMsg, path_.c_str());
94 sqlite3_free(errMsg);
95 }
96 int32_t rettmp = DeleteAndBackup(ret);
97 if (rettmp == SQLITE_OK && rettmp != ret) {
98 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
99 int32_t ret = sqlite3_exec(sqlite_, sql.c_str(), callback, recv, &errMsg);
100 lock.unlock();
101 }
102
103 return rettmp == SQLITE_OK ? NETMANAGER_SUCCESS : NETMANAGER_ERROR;
104 }
105
CreateTable(const std::string & tableName,const std::string & tableInfo)106 int32_t NetStatsDatabaseHelper::CreateTable(const std::string &tableName, const std::string &tableInfo)
107 {
108 std::string sql = CREATE_TABLE_IF_NOT_EXISTS + tableName + "(" + tableInfo + ");";
109 int32_t ret = ExecSql(sql, nullptr, sqlCallback);
110 if (ret != NETMANAGER_SUCCESS) {
111 return STATS_ERR_CREATE_TABLE_FAIL;
112 }
113 return NETMANAGER_SUCCESS;
114 }
115
Open(const std::string & path)116 int32_t NetStatsDatabaseHelper::Open(const std::string &path)
117 {
118 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
119 int32_t ret = sqlite3_open_v2(path.c_str(), &sqlite_,
120 SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE | SQLITE_OPEN_FULLMUTEX, nullptr);
121 return ret == SQLITE_OK ? NETMANAGER_SUCCESS : NETMANAGER_ERROR;
122 }
123
InsertData(const std::string & tableName,const std::string & paramList,const NetStatsInfo & info)124 int32_t NetStatsDatabaseHelper::InsertData(const std::string &tableName, const std::string ¶mList,
125 const NetStatsInfo &info)
126 {
127 std::string params;
128 int32_t paramCount = count(paramList.begin(), paramList.end(), ',') + 1;
129 for (int32_t i = 0; i < paramCount; ++i) {
130 params += "?";
131 if (i != paramCount - 1) {
132 params += ",";
133 }
134 }
135 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
136 std::string sql = "INSERT INTO " + tableName + " (" + paramList + ") " + "VALUES" + " (" + params + ") ";
137 int32_t ret = statement_.Prepare(sqlite_, sql);
138 int32_t rettmp = DeleteAndBackup(ret);
139 if (rettmp != SQLITE_OK) {
140 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
141 return STATS_ERR_WRITE_DATA_FAIL;
142 }
143 if (rettmp != ret) {
144 statement_.Prepare(sqlite_, sql);
145 }
146 int32_t idx = 1;
147 if (paramCount == UID_PARAM_NUM) {
148 statement_.BindInt64(idx, info.uid_);
149 ++idx;
150 }
151 statement_.BindText(idx, info.iface_);
152 statement_.BindInt64(++idx, info.date_);
153 statement_.BindInt64(++idx, info.rxBytes_);
154 statement_.BindInt64(++idx, info.rxPackets_);
155 statement_.BindInt64(++idx, info.txBytes_);
156 statement_.BindInt64(++idx, info.txPackets_);
157 if (paramCount == UID_PARAM_NUM) {
158 statement_.BindText(++idx, info.ident_);
159 }
160 statement_.BindInt64(++idx, info.flag_);
161 statement_.BindInt64(++idx, info.userId_);
162 ret = statement_.Step();
163 statement_.ResetStatementAndClearBindings();
164 if (ret != SQLITE_DONE) {
165 NETMGR_LOG_E("Step failed ret:%{public}d", ret);
166 return STATS_ERR_WRITE_DATA_FAIL;
167 }
168 return NETMANAGER_SUCCESS;
169 }
170
SelectData(std::vector<NetStatsInfo> & infos,const std::string & tableName,uint64_t start,uint64_t end)171 int32_t NetStatsDatabaseHelper::SelectData(std::vector<NetStatsInfo> &infos, const std::string &tableName,
172 uint64_t start, uint64_t end)
173 {
174 infos.clear();
175 std::string sql = SELECT_FROM + tableName + " t WHERE 1=1" + DATA_MORE_THAN + DATA_LESS_THAN;
176 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
177 int32_t ret = statement_.Prepare(sqlite_, sql);
178 int32_t rettmp = DeleteAndBackup(ret);
179 if (rettmp != SQLITE_OK) {
180 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
181 return STATS_ERR_READ_DATA_FAIL;
182 }
183 if (rettmp != ret) {
184 statement_.Prepare(sqlite_, sql);
185 }
186 int32_t idx = 1;
187 ret = statement_.BindInt64(idx, start);
188 if (ret != SQLITE_OK) {
189 NETMGR_LOG_E("Bind int64 failed ret:%{public}d", ret);
190 return STATS_ERR_READ_DATA_FAIL;
191 }
192 ret = statement_.BindInt64(++idx, end);
193 if (ret != SQLITE_OK) {
194 NETMGR_LOG_E("Bind int64 failed ret:%{public}d", ret);
195 return STATS_ERR_READ_DATA_FAIL;
196 }
197 return Step(infos);
198 }
199
SelectData(const uint32_t uid,uint64_t start,uint64_t end,std::vector<NetStatsInfo> & infos)200 int32_t NetStatsDatabaseHelper::SelectData(const uint32_t uid, uint64_t start, uint64_t end,
201 std::vector<NetStatsInfo> &infos)
202 {
203 infos.clear();
204 std::string sql = SELECT_FROM + std::string(UID_TABLE) + " t WHERE 1=1 AND t.UID == ?" + DATA_MORE_THAN +
205 DATA_LESS_THAN;
206 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
207 int32_t ret = statement_.Prepare(sqlite_, sql);
208 int32_t rettmp = DeleteAndBackup(ret);
209 if (rettmp != SQLITE_OK) {
210 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
211 return STATS_ERR_READ_DATA_FAIL;
212 }
213 if (rettmp != ret) {
214 statement_.Prepare(sqlite_, sql);
215 }
216 int32_t idx = 1;
217 ret = statement_.BindInt64(idx, uid);
218 if (ret != SQLITE_OK) {
219 NETMGR_LOG_E("Bind int32 failed ret:%{public}d", ret);
220 return STATS_ERR_READ_DATA_FAIL;
221 }
222 ret = BindInt64(idx, start, end);
223 if (ret != SQLITE_OK) {
224 return ret;
225 }
226 return Step(infos);
227 }
228
SelectData(const std::string & iface,uint64_t start,uint64_t end,std::vector<NetStatsInfo> & infos)229 int32_t NetStatsDatabaseHelper::SelectData(const std::string &iface, uint64_t start, uint64_t end,
230 std::vector<NetStatsInfo> &infos)
231 {
232 infos.clear();
233 std::string sql = SELECT_FROM + std::string(IFACE_TABLE) + " t WHERE 1=1 AND t.IFace = ?" +
234 DATA_MORE_THAN + DATA_LESS_THAN;
235 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
236 int32_t ret = statement_.Prepare(sqlite_, sql);
237 int32_t rettmp = DeleteAndBackup(ret);
238 if (rettmp != SQLITE_OK) {
239 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
240 return STATS_ERR_READ_DATA_FAIL;
241 }
242 if (rettmp != ret) {
243 statement_.Prepare(sqlite_, sql);
244 }
245 int32_t idx = 1;
246 ret = statement_.BindText(idx, iface);
247 if (ret != SQLITE_OK) {
248 NETMGR_LOG_E("Bind text failed ret:%{public}d", ret);
249 return STATS_ERR_READ_DATA_FAIL;
250 }
251 ret = BindInt64(idx, start, end);
252 if (ret != SQLITE_OK) {
253 return ret;
254 }
255 return Step(infos);
256 }
257
SelectData(const std::string & iface,const uint32_t uid,uint64_t start,uint64_t end,std::vector<NetStatsInfo> & infos)258 int32_t NetStatsDatabaseHelper::SelectData(const std::string &iface, const uint32_t uid, uint64_t start, uint64_t end,
259 std::vector<NetStatsInfo> &infos)
260 {
261 infos.clear();
262 std::string sql = SELECT_FROM + std::string(UID_TABLE) + " t WHERE 1=1 AND t.UID = ?" + " AND t.IFace = ?" +
263 DATA_MORE_THAN + DATA_LESS_THAN;
264 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
265 int32_t ret = statement_.Prepare(sqlite_, sql);
266 int32_t rettmp = DeleteAndBackup(ret);
267 if (rettmp != SQLITE_OK) {
268 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
269 return STATS_ERR_READ_DATA_FAIL;
270 }
271 if (rettmp != ret) {
272 statement_.Prepare(sqlite_, sql);
273 }
274 int32_t idx = 1;
275 ret = statement_.BindInt64(idx, uid);
276 if (ret != SQLITE_OK) {
277 NETMGR_LOG_E("bind int32 ret:%{public}d", ret);
278 return STATS_ERR_READ_DATA_FAIL;
279 }
280 ret = statement_.BindText(++idx, iface);
281 if (ret != SQLITE_OK) {
282 NETMGR_LOG_E("Bind text failed ret:%{public}d", ret);
283 return STATS_ERR_READ_DATA_FAIL;
284 }
285 ret = BindInt64(idx, start, end);
286 if (ret != SQLITE_OK) {
287 return ret;
288 }
289 return Step(infos);
290 }
291
QueryData(const std::string & tableName,const std::string & ident,uint64_t start,uint64_t end,std::vector<NetStatsInfo> & infos)292 int32_t NetStatsDatabaseHelper::QueryData(const std::string &tableName, const std::string &ident, uint64_t start,
293 uint64_t end, std::vector<NetStatsInfo> &infos)
294 {
295 infos.clear();
296 std::string sql =
297 SELECT_FROM + tableName + " t WHERE 1=1 AND t.Ident = ?" + DATA_MORE_THAN + DATA_LESS_THAN;
298 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
299 int32_t ret = statement_.Prepare(sqlite_, sql);
300 int32_t rettmp = DeleteAndBackup(ret);
301 if (rettmp != SQLITE_OK) {
302 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
303 return STATS_ERR_READ_DATA_FAIL;
304 }
305 if (rettmp != ret) {
306 statement_.Prepare(sqlite_, sql);
307 }
308 int32_t idx = 1;
309 ret = statement_.BindText(idx, ident);
310 if (ret != SQLITE_OK) {
311 NETMGR_LOG_E("bind text ret:%{public}d", ret);
312 return STATS_ERR_READ_DATA_FAIL;
313 }
314 ret = BindInt64(idx, start, end);
315 if (ret != SQLITE_OK) {
316 return ret;
317 }
318 return Step(infos);
319 }
320
QueryData(const std::string & tableName,const std::string & ident,const int32_t userId,uint64_t start,uint64_t end,std::vector<NetStatsInfo> & infos)321 int32_t NetStatsDatabaseHelper::QueryData(const std::string &tableName, const std::string &ident, const int32_t userId,
322 uint64_t start, uint64_t end, std::vector<NetStatsInfo> &infos)
323 {
324 infos.clear();
325 std::string sql =
326 SELECT_FROM + tableName + " t WHERE 1=1 AND t.Ident = ? " + " AND t.UserId = ? " +
327 DATA_MORE_THAN + DATA_LESS_THAN;
328 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
329 int32_t ret = statement_.Prepare(sqlite_, sql);
330 if (ret != SQLITE_OK) {
331 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
332 return STATS_ERR_READ_DATA_FAIL;
333 }
334 int32_t idx = 1;
335 ret = statement_.BindText(idx, ident);
336 if (ret != SQLITE_OK) {
337 NETMGR_LOG_E("bind text ret:%{public}d", ret);
338 return STATS_ERR_READ_DATA_FAIL;
339 }
340 ret = statement_.BindInt32(++idx, userId);
341 if (ret != SQLITE_OK) {
342 return ret;
343 }
344 ret = BindInt64(idx, start, end);
345 if (ret != SQLITE_OK) {
346 return ret;
347 }
348 return Step(infos);
349 }
350
QueryData(const std::string & tableName,const uint32_t uid,const std::string & ident,uint64_t start,uint64_t end,std::vector<NetStatsInfo> & infos)351 int32_t NetStatsDatabaseHelper::QueryData(const std::string &tableName, const uint32_t uid, const std::string &ident,
352 uint64_t start, uint64_t end, std::vector<NetStatsInfo> &infos)
353 {
354 infos.clear();
355 std::string sql = SELECT_FROM + tableName + " t WHERE 1=1 AND T.UID = ? AND t.Ident = ?" + DATA_MORE_THAN +
356 DATA_LESS_THAN;
357 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
358 int32_t ret = statement_.Prepare(sqlite_, sql);
359 int32_t rettmp = DeleteAndBackup(ret);
360 if (rettmp != SQLITE_OK) {
361 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
362 return STATS_ERR_READ_DATA_FAIL;
363 }
364 if (rettmp != ret) {
365 statement_.Prepare(sqlite_, sql);
366 }
367 int32_t idx = 1;
368 ret = statement_.BindInt64(idx, uid);
369 if (ret != SQLITE_OK) {
370 NETMGR_LOG_E("bind int32 ret:%{public}d", ret);
371 return STATS_ERR_READ_DATA_FAIL;
372 }
373 ret = statement_.BindText(++idx, ident);
374 if (ret != SQLITE_OK) {
375 NETMGR_LOG_E("bind text ret:%{public}d", ret);
376 return STATS_ERR_READ_DATA_FAIL;
377 }
378 ret = BindInt64(idx, start, end);
379 if (ret != SQLITE_OK) {
380 return ret;
381 }
382 return Step(infos);
383 }
384
DeleteData(const std::string & tableName,uint64_t start,uint64_t end)385 int32_t NetStatsDatabaseHelper::DeleteData(const std::string &tableName, uint64_t start, uint64_t end)
386 {
387 std::string sql =
388 DELETE_FROM + tableName + " WHERE Date >= " + std::to_string(start) + " AND Date <= " + std::to_string(end);
389 return ExecSql(sql, nullptr, sqlCallback);
390 }
391
DeleteData(const std::string & tableName,uint64_t uid)392 int32_t NetStatsDatabaseHelper::DeleteData(const std::string &tableName, uint64_t uid)
393 {
394 std::string sql = DELETE_FROM + tableName + " WHERE UID = ?";
395 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
396 int32_t ret = statement_.Prepare(sqlite_, sql);
397 int32_t rettmp = DeleteAndBackup(ret);
398 if (rettmp != SQLITE_OK) {
399 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
400 return STATS_ERR_WRITE_DATA_FAIL;
401 }
402 if (rettmp != ret) {
403 statement_.Prepare(sqlite_, sql);
404 }
405 int32_t idx = 1;
406 statement_.BindInt64(idx, uid);
407 ret = statement_.Step();
408 statement_.ResetStatementAndClearBindings();
409 if (ret != SQLITE_DONE) {
410 NETMGR_LOG_E("Step failed ret:%{public}d", ret);
411 return STATS_ERR_WRITE_DATA_FAIL;
412 }
413 return NETMANAGER_SUCCESS;
414 }
415
Close()416 int32_t NetStatsDatabaseHelper::Close()
417 {
418 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
419 int32_t ret = sqlite3_close_v2(sqlite_);
420 return ret == SQLITE_OK ? NETMANAGER_SUCCESS : NETMANAGER_ERROR;
421 }
422
ClearData(const std::string & tableName)423 int32_t NetStatsDatabaseHelper::ClearData(const std::string &tableName)
424 {
425 std::string sql = DELETE_FROM + tableName;
426 std::string shrinkMemSql = "PRAGMA shrink_memory";
427 int32_t execSqlRet = ExecSql(sql, nullptr, sqlCallback);
428 if (execSqlRet != NETMANAGER_SUCCESS) {
429 NETMGR_LOG_E("Delete data failed");
430 return execSqlRet;
431 }
432 execSqlRet = ExecSql(shrinkMemSql, nullptr, sqlCallback);
433 if (execSqlRet != NETMANAGER_SUCCESS) {
434 NETMGR_LOG_E("Delete data failed");
435 return execSqlRet;
436 }
437 sql = "VACUUM";
438 execSqlRet = ExecSql(sql, nullptr, sqlCallback);
439 if (execSqlRet != NETMANAGER_SUCCESS) {
440 NETMGR_LOG_E("Delete data failed");
441 return execSqlRet;
442 }
443 return ExecSql(shrinkMemSql, nullptr, sqlCallback);
444 }
445
Step(std::vector<NetStatsInfo> & infos)446 int32_t NetStatsDatabaseHelper::Step(std::vector<NetStatsInfo> &infos)
447 {
448 int32_t rc = statement_.Step();
449 NETMGR_LOG_D("Step result:%{public}d", rc);
450 while (rc != SQLITE_DONE) {
451 if (rc != SQLITE_ROW) {
452 NETMGR_LOG_E("sqlite step error: %{public}d", rc);
453 statement_.ResetStatementAndClearBindings();
454 return STATS_ERR_READ_DATA_FAIL;
455 }
456 int32_t i = 0;
457 NetStatsInfo info;
458 if (statement_.GetColumnCount() == UID_PARAM_NUM) {
459 statement_.GetColumnInt(i, info.uid_);
460 ++i;
461 }
462 statement_.GetColumnString(i, info.iface_);
463 statement_.GetColumnLong(++i, info.date_);
464 statement_.GetColumnLong(++i, info.rxBytes_);
465 statement_.GetColumnLong(++i, info.rxPackets_);
466 statement_.GetColumnLong(++i, info.txBytes_);
467 statement_.GetColumnLong(++i, info.txPackets_);
468 if (statement_.GetColumnCount() == UID_PARAM_NUM) {
469 statement_.GetColumnString(++i, info.ident_);
470 }
471 statement_.GetColumnInt(++i, info.flag_);
472 statement_.GetColumnInt(++i, info.userId_);
473 infos.emplace_back(info);
474 rc = statement_.Step();
475 NETMGR_LOG_D("Step result:%{public}d", rc);
476 }
477 statement_.ResetStatementAndClearBindings();
478 return NETMANAGER_SUCCESS;
479 }
480
BindInt64(int32_t idx,uint64_t start,uint64_t end)481 int32_t NetStatsDatabaseHelper::BindInt64(int32_t idx, uint64_t start, uint64_t end)
482 {
483 int32_t ret = statement_.BindInt64(++idx, start);
484 if (ret != SQLITE_OK) {
485 NETMGR_LOG_E("Bind int64 failed ret:%{public}d", ret);
486 return STATS_ERR_READ_DATA_FAIL;
487 }
488 ret = statement_.BindInt64(++idx, end);
489 if (ret != SQLITE_OK) {
490 NETMGR_LOG_E("Bind int64 failed ret:%{public}d", ret);
491 return STATS_ERR_READ_DATA_FAIL;
492 }
493
494 return ret;
495 }
496
Upgrade()497 int32_t NetStatsDatabaseHelper::Upgrade()
498 {
499 auto ret = ExecTableUpgrade(UID_TABLE, Version_1);
500 if (ret != NETMANAGER_SUCCESS) {
501 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_TABLE, Version_1);
502 }
503 ret = ExecTableUpgrade(UID_SIM_TABLE, Version_2);
504 if (ret != NETMANAGER_SUCCESS) {
505 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_SIM_TABLE, Version_2);
506 }
507 ret = ExecTableUpgrade(UID_TABLE, Version_3);
508 if (ret != NETMANAGER_SUCCESS) {
509 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_TABLE, Version_3);
510 }
511 ret = ExecTableUpgrade(UID_SIM_TABLE, Version_3);
512 if (ret != NETMANAGER_SUCCESS) {
513 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_SIM_TABLE, Version_3);
514 }
515 ret = ExecTableUpgrade(UID_SIM_TABLE, Version_4);
516 if (ret != NETMANAGER_SUCCESS) {
517 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_SIM_TABLE, Version_4);
518 }
519 ret = ExecTableUpgrade(UID_SIM_TABLE, Version_5);
520 if (ret != NETMANAGER_SUCCESS) {
521 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_SIM_TABLE, Version_5);
522 }
523 ret = ExecTableUpgrade(UID_TABLE, Version_6);
524 if (ret != NETMANAGER_SUCCESS) {
525 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_SIM_TABLE, Version_6);
526 }
527 ret = ExecTableUpgrade(UID_SIM_TABLE, Version_6);
528 if (ret != NETMANAGER_SUCCESS) {
529 NETMGR_LOG_E("Upgrade db failed. table is %{public}s, version is %{public}d", UID_SIM_TABLE, Version_6);
530 }
531 return ret;
532 }
533
ExecTableUpgrade(const std::string & tableName,TableVersion newVersion)534 int32_t NetStatsDatabaseHelper::ExecTableUpgrade(const std::string &tableName, TableVersion newVersion)
535 {
536 TableVersion oldVersion;
537 auto ret = GetTableVersion(oldVersion, tableName);
538 if (ret != SQLITE_OK) {
539 NETMGR_LOG_E("ExecTableUpgrade getTableVersion failed. ret = %{public}d", ret);
540 return NETMANAGER_ERROR;
541 }
542 if (oldVersion == newVersion) {
543 return NETMANAGER_SUCCESS;
544 }
545 NETMGR_LOG_I("ExecTableUpgrade tableName = %{public}s, oldVersion = %{public}d, newVersion = %{public}d",
546 tableName.c_str(), oldVersion, newVersion);
547 ExecUpgradeSql(tableName, oldVersion, newVersion);
548 if (oldVersion != newVersion) {
549 NETMGR_LOG_E("ExecTableUpgrade error. oldVersion = %{public}d, newVersion = %{public}d",
550 oldVersion, newVersion);
551 return NETMANAGER_ERROR;
552 }
553 ret = UpdateTableVersion(oldVersion, tableName);
554 if (ret != NETMANAGER_SUCCESS) {
555 NETMGR_LOG_E("ExecTableUpgrade updateVersion failed. ret = %{public}d", ret);
556 return NETMANAGER_ERROR;
557 }
558 return NETMANAGER_SUCCESS;
559 }
560
ExecUpgradeSql(const std::string & tableName,TableVersion & oldVersion,TableVersion newVersion)561 void NetStatsDatabaseHelper::ExecUpgradeSql(const std::string &tableName, TableVersion &oldVersion,
562 TableVersion newVersion)
563 {
564 int32_t ret = NETMANAGER_SUCCESS;
565 if (oldVersion < Version_1 && newVersion >= Version_1) {
566 std::string sql = ALTER_TABLE + tableName + " ADD COLUMN Ident CHAR(100) NOT NULL DEFAULT '';";
567 ret = ExecSql(sql, nullptr, sqlCallback);
568 if (ret != SQLITE_OK) {
569 NETMGR_LOG_E("ExecTableUpgrade version_1 failed. ret = %{public}d", ret);
570 }
571 oldVersion = Version_1;
572 }
573 if (oldVersion < Version_2 && newVersion >= Version_2) {
574 ret = DeleteData(tableName, Sim_UID);
575 if (ret != SQLITE_OK) {
576 NETMGR_LOG_E("ExecTableUpgrade Version_2 failed. ret = %{public}d", ret);
577 }
578 oldVersion = Version_2;
579 }
580 if (oldVersion < Version_3 && newVersion >= Version_3) {
581 std::string sql = ALTER_TABLE + tableName + " ADD COLUMN Flag INTEGER NOT NULL DEFAULT 0;";
582 ret = ExecSql(sql, nullptr, sqlCallback);
583 if (ret != SQLITE_OK) {
584 NETMGR_LOG_E("ExecTableUpgrade version_3 failed. ret = %{public}d", ret);
585 }
586 oldVersion = Version_3;
587 }
588 if (oldVersion < Version_4 && newVersion >= Version_4) {
589 std::string sql = UPDATE + tableName + SET_FLAG + std::to_string(STATS_DATA_FLAG_SIM) +
590 " WHERE Flag = " + std::to_string(STATS_DATA_FLAG_DEFAULT) + ";";
591 ret = ExecSql(sql, nullptr, sqlCallback);
592 if (ret != SQLITE_OK) {
593 NETMGR_LOG_E("ExecTableUpgrade Version_4 failed. ret = %{public}d", ret);
594 }
595 oldVersion = Version_4;
596 }
597 if (oldVersion < Version_5 && newVersion >= Version_5) {
598 if (isDisplayTrafficAncoList_) {
599 std::string sqlsim = UPDATE + tableName + SET_FLAG + std::to_string(STATS_DATA_FLAG_SIM_BASIC) +
600 " WHERE Flag = " + std::to_string(STATS_DATA_FLAG_SIM) + ";";
601 ret = ExecSql(sqlsim, nullptr, sqlCallback);
602 std::string sqlsim2 = UPDATE + tableName + SET_FLAG + std::to_string(STATS_DATA_FLAG_SIM2_BASIC) +
603 " WHERE Flag = " + std::to_string(STATS_DATA_FLAG_SIM2) + ";";
604 int32_t retsim2 = ExecSql(sqlsim2, nullptr, sqlCallback);
605 if (ret != SQLITE_OK || retsim2 != SQLITE_OK) {
606 NETMGR_LOG_E("ExecTableUpgrade Version_5 failed. ret = %{public}d", ret);
607 }
608 }
609 oldVersion = Version_5;
610 }
611 ExecUpgradeSqlNext(tableName, oldVersion, newVersion);
612 }
613
ExecUpgradeSqlNext(const std::string & tableName,TableVersion & oldVersion,TableVersion newVersion)614 void NetStatsDatabaseHelper::ExecUpgradeSqlNext(const std::string &tableName, TableVersion &oldVersion,
615 TableVersion newVersion)
616 {
617 int32_t ret = NETMANAGER_SUCCESS;
618 if (oldVersion < Version_6 && newVersion >= Version_6) {
619 std::string sql = ALTER_TABLE + tableName + " ADD COLUMN UserId INTEGER NOT NULL DEFAULT 0;";
620 ret = ExecSql(sql, nullptr, sqlCallback);
621 if (ret != SQLITE_OK) {
622 NETMGR_LOG_E("ExecTableUpgrade Version_6 failed. ret = %{public}d", ret);
623 }
624 oldVersion = Version_6;
625 }
626 }
627
GetTableVersion(TableVersion & version,const std::string & tableName)628 int32_t NetStatsDatabaseHelper::GetTableVersion(TableVersion &version, const std::string &tableName)
629 {
630 std::string sql = SELECT_FROM + std::string(VERSION_TABLE) + " WHERE Name = ?;";
631 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
632 int32_t ret = statement_.Prepare(sqlite_, sql);
633 int32_t rettmp = DeleteAndBackup(ret);
634 if (rettmp != SQLITE_OK) {
635 NETMGR_LOG_E("Prepare failed ret:%{public}d", ret);
636 return STATS_ERR_READ_DATA_FAIL;
637 }
638 if (rettmp != ret) {
639 statement_.Prepare(sqlite_, sql);
640 }
641 int32_t idx = 1;
642 ret = statement_.BindText(idx, tableName);
643 if (ret != SQLITE_OK) {
644 NETMGR_LOG_E("bind text ret:%{public}d", ret);
645 return STATS_ERR_READ_DATA_FAIL;
646 }
647 int32_t rc = statement_.Step();
648 auto v = static_cast<uint32_t>(Version_0);
649 while (rc != SQLITE_DONE) {
650 if (rc == SQLITE_ROW) {
651 int32_t i = 1;
652 statement_.GetColumnInt(i, v);
653 rc = statement_.Step();
654 } else {
655 NETMGR_LOG_E("Step failed with rc:%{public}d", rc);
656 break;
657 }
658 }
659 statement_.ResetStatementAndClearBindings();
660 version = static_cast<TableVersion>(v);
661 return NETMANAGER_SUCCESS;
662 }
663
UpdateTableVersion(TableVersion version,const std::string & tableName)664 int32_t NetStatsDatabaseHelper::UpdateTableVersion(TableVersion version, const std::string &tableName)
665 {
666 std::string sql = INSERT_OR_REPLACE_INTO + std::string(VERSION_TABLE) + "(Name, Version) VALUES('" +
667 tableName + "', " + std::to_string(version) + ");";
668 return ExecSql(sql, nullptr, sqlCallback);
669 }
670
UpdateStatsFlag(const std::string & tableName,uint32_t uid,uint32_t flag)671 int32_t NetStatsDatabaseHelper::UpdateStatsFlag(const std::string &tableName, uint32_t uid, uint32_t flag)
672 {
673 std::string sql = UPDATE + tableName + SET_FLAG + std::to_string(flag) +
674 " WHERE UID = " + std::to_string(uid);
675 return ExecSql(sql, nullptr, sqlCallback);
676 }
677
UpdateStatsFlagByUserId(const std::string & tableName,int32_t userId,uint32_t flag)678 int32_t NetStatsDatabaseHelper::UpdateStatsFlagByUserId(const std::string &tableName, int32_t userId, uint32_t flag)
679 {
680 std::string sql = UPDATE + tableName + SET_FLAG + std::to_string(flag) +
681 " WHERE UserId = " + std::to_string(userId);
682 return ExecSql(sql, nullptr, sqlCallback);
683 }
684
UpdateStatsUserIdByUserId(const std::string & tableName,int32_t oldUserId,int32_t newUserId)685 int32_t NetStatsDatabaseHelper::UpdateStatsUserIdByUserId(const std::string &tableName,
686 int32_t oldUserId, int32_t newUserId)
687 {
688 std::string sql = UPDATE + tableName + SET_USERID + std::to_string(newUserId) +
689 " WHERE UserId = " + std::to_string(oldUserId);
690 return ExecSql(sql, nullptr, sqlCallback);
691 }
692
UpdateDataFlag(const std::string & tableName,uint32_t oldFlag,uint32_t newFlag)693 int32_t NetStatsDatabaseHelper::UpdateDataFlag(const std::string &tableName, uint32_t oldFlag, uint32_t newFlag)
694 {
695 std::string sql =
696 UPDATE + tableName + SET_FLAG + std::to_string(newFlag) + " WHERE Flag = " + std::to_string(oldFlag);
697 return ExecSql(sql, nullptr, sqlCallback);
698 }
699
BackupNetStatsData(const std::string & sourceDb,const std::string & backupDb)700 bool NetStatsDatabaseHelper::BackupNetStatsData(const std::string &sourceDb, const std::string &backupDb)
701 {
702 NETMGR_LOG_I("BackupNetStatsData start");
703 sqlite3* source = nullptr;
704 sqlite3* backup = nullptr;
705 int32_t ret = sqlite3_open(sourceDb.c_str(), &source);
706 if (ret != SQLITE_OK) {
707 NETMGR_LOG_E("sqlite3_open failed ret:%{public}d", ret);
708 return false;
709 }
710 ret = sqlite3_open(backupDb.c_str(), &backup);
711 if (ret != SQLITE_OK) {
712 NETMGR_LOG_E("sqlite3_open failed ret:%{public}d", ret);
713 return false;
714 }
715
716 sqlite3_backup* pBackup = sqlite3_backup_init(backup, "main", source, "main");
717 int rc = -1;
718 if (pBackup) {
719 while ((rc = sqlite3_backup_step(pBackup, -1)) == SQLITE_OK || rc == SQLITE_BUSY || rc == SQLITE_LOCKED) {
720 if (rc == SQLITE_BUSY || rc == SQLITE_LOCKED) {
721 break;
722 }
723 }
724 if (rc != SQLITE_DONE) {
725 NETMGR_LOG_E("Backup failed: %{public}s, ret: %{public}d", sqlite3_errmsg(backup), rc);
726 } else {
727 NETMGR_LOG_E("Backup completed successfully");
728 }
729 sqlite3_backup_finish(pBackup);
730 } else {
731 NETMGR_LOG_E("Failed to initialize backup: %{public}s", sqlite3_errmsg(backup));
732 }
733
734 sqlite3_close(source);
735 sqlite3_close(backup);
736 return (rc == SQLITE_DONE);
737 }
738
BackupNetStatsDataDB(const std::string & sourceDb,const std::string & backupDb)739 bool NetStatsDatabaseHelper::BackupNetStatsDataDB(const std::string &sourceDb, const std::string &backupDb)
740 {
741 NETMGR_LOG_I("BackupNetStatsDataDB");
742 std::unique_lock<ffrt::mutex> lock(sqliteMutex_);
743 bool ret = BackupNetStatsData(sourceDb, backupDb);
744 return ret;
745 }
746
DeleteAndBackup(int32_t errCode)747 int32_t NetStatsDatabaseHelper::DeleteAndBackup(int32_t errCode)
748 {
749 if (errCode != SQLITE_NOTADB || (path_ != NET_STATS_DATABASE_BACK_PATH &&
750 path_ != NET_STATS_DATABASE_PATH)) {
751 return errCode;
752 }
753 if (path_.find(NET_STATS_DATABASE_BACK_PATH) != std::string::npos) {
754 CommonUtils::DeleteFile(NET_STATS_DATABASE_BACK_PATH);
755 return errCode;
756 }
757
758 CommonUtils::DeleteFile(NET_STATS_DATABASE_PATH);
759 bool backupRet = BackupNetStatsData(NET_STATS_DATABASE_BACK_PATH, NET_STATS_DATABASE_PATH);
760 if (backupRet) {
761 return SQLITE_OK;
762 }
763
764 return errCode;
765 }
766 } // namespace NetManagerStandard
767 } // namespace OHOS
768