xref: /developtools/hdc/src/common/decompress.cpp (revision cc290419)
1cc290419Sopenharmony_ci/*
2cc290419Sopenharmony_ci * Copyright (C) 2024 Huawei Device Co., Ltd.
3cc290419Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
4cc290419Sopenharmony_ci * you may not use this file except in compliance with the License.
5cc290419Sopenharmony_ci * You may obtain a copy of the License at
6cc290419Sopenharmony_ci *
7cc290419Sopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
8cc290419Sopenharmony_ci *
9cc290419Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
10cc290419Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
11cc290419Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12cc290419Sopenharmony_ci * See the License for the specific language governing permissions and
13cc290419Sopenharmony_ci * limitations under the License.
14cc290419Sopenharmony_ci */
15cc290419Sopenharmony_ci#include "decompress.h"
16cc290419Sopenharmony_ci
17cc290419Sopenharmony_ci#include <sstream>
18cc290419Sopenharmony_ci#include <fstream>
19cc290419Sopenharmony_ci#include <optional>
20cc290419Sopenharmony_ci#include <iostream>
21cc290419Sopenharmony_ci
22cc290419Sopenharmony_cinamespace Hdc {
23cc290419Sopenharmony_cibool Decompress::DecompressToLocal(std::string decPath)
24cc290419Sopenharmony_ci{
25cc290419Sopenharmony_ci    if (!CheckPath(decPath)) {
26cc290419Sopenharmony_ci        return false;
27cc290419Sopenharmony_ci    }
28cc290419Sopenharmony_ci    uint8_t buff[HEADER_LEN];
29cc290419Sopenharmony_ci    std::ifstream inFile(tarPath);
30cc290419Sopenharmony_ci    std::optional<Entry> entry = std::nullopt;
31cc290419Sopenharmony_ci    while (true) {
32cc290419Sopenharmony_ci        inFile.read(reinterpret_cast<char*>(buff), HEADER_LEN);
33cc290419Sopenharmony_ci        auto readcnt = inFile.gcount();
34cc290419Sopenharmony_ci        if (readcnt == 0) {
35cc290419Sopenharmony_ci            break;
36cc290419Sopenharmony_ci        }
37cc290419Sopenharmony_ci        if (inFile.fail() || readcnt != HEADER_LEN) {
38cc290419Sopenharmony_ci            WRITE_LOG(LOG_FATAL, "read file error");
39cc290419Sopenharmony_ci            break;
40cc290419Sopenharmony_ci        }
41cc290419Sopenharmony_ci        entry = Entry(buff, HEADER_LEN);
42cc290419Sopenharmony_ci        if (!entry.value().CopyPayload(decPath, inFile)) {
43cc290419Sopenharmony_ci            entry = std::nullopt;
44cc290419Sopenharmony_ci            break;
45cc290419Sopenharmony_ci        }
46cc290419Sopenharmony_ci        entry = std::nullopt;
47cc290419Sopenharmony_ci        continue;
48cc290419Sopenharmony_ci    }
49cc290419Sopenharmony_ci    inFile.close();
50cc290419Sopenharmony_ci    return true;
51cc290419Sopenharmony_ci}
52cc290419Sopenharmony_ci
53cc290419Sopenharmony_cibool Decompress::CheckPath(std::string decPath)
54cc290419Sopenharmony_ci{
55cc290419Sopenharmony_ci    uv_fs_t req;
56cc290419Sopenharmony_ci    int rc = uv_fs_lstat(nullptr, &req, tarPath.c_str(), nullptr);
57cc290419Sopenharmony_ci    uv_fs_req_cleanup(&req);
58cc290419Sopenharmony_ci    if (rc != 0 || !(req.statbuf.st_mode & S_IFREG)) {
59cc290419Sopenharmony_ci        WRITE_LOG(LOG_FATAL, "%s not exist, or not file", tarPath.c_str());
60cc290419Sopenharmony_ci        return false;
61cc290419Sopenharmony_ci    }
62cc290419Sopenharmony_ci    auto fileSize = req.statbuf.st_size;
63cc290419Sopenharmony_ci    if (fileSize == 0 || fileSize % HEADER_LEN != 0) {
64cc290419Sopenharmony_ci        WRITE_LOG(LOG_FATAL, "file is not tar %s", tarPath.c_str());
65cc290419Sopenharmony_ci        return false;
66cc290419Sopenharmony_ci    }
67cc290419Sopenharmony_ci    rc = uv_fs_lstat(nullptr, &req, decPath.c_str(), nullptr);
68cc290419Sopenharmony_ci    uv_fs_req_cleanup(&req);
69cc290419Sopenharmony_ci    if (rc == 0) {
70cc290419Sopenharmony_ci        if (req.statbuf.st_mode & S_IFREG) {
71cc290419Sopenharmony_ci            WRITE_LOG(LOG_FATAL, "path is exist, and path not dir %s", decPath.c_str());
72cc290419Sopenharmony_ci            return false;
73cc290419Sopenharmony_ci        }
74cc290419Sopenharmony_ci    } else {
75cc290419Sopenharmony_ci        std::string estr;
76cc290419Sopenharmony_ci        bool b = Base::TryCreateDirectory(decPath, estr);
77cc290419Sopenharmony_ci        if (!b) {
78cc290419Sopenharmony_ci            WRITE_LOG(LOG_FATAL, "mkdir failed decPath:%s estr:%s", decPath.c_str(), estr.c_str());
79cc290419Sopenharmony_ci            return false;
80cc290419Sopenharmony_ci        }
81cc290419Sopenharmony_ci    }
82cc290419Sopenharmony_ci    return true;
83cc290419Sopenharmony_ci}
84cc290419Sopenharmony_ci}