1 /*
2  * Copyright (c) 2021 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 #ifndef IMAGE_PATCH_H
17 #define IMAGE_PATCH_H
18 
19 #include <sys/types.h>
20 #include "deflate_adapter.h"
21 #include "diffpatch.h"
22 #include "openssl/sha.h"
23 #include "package/pkg_manager.h"
24 #include "securec.h"
25 
26 namespace UpdatePatch {
27 class ImagePatch {
28 public:
ImagePatch(UpdatePatchWriterPtr writer)29     explicit ImagePatch(UpdatePatchWriterPtr writer) : writer_(writer) {}
30     virtual ~ImagePatch() = default;
31 
32     virtual int32_t ApplyImagePatch(const PatchParam &param, size_t &startOffset) = 0;
33 
34     template<typename T>
ReadLE(const uint8_t * address)35     static T ReadLE(const uint8_t *address)
36     {
37         T result;
38         errno_t ret = memcpy_s(&result, sizeof(result), address, sizeof(T));
39         if (ret != EOK) {
40             // only warning no need to return invalid value
41             PATCH_LOGE("Failed to memcpy");
42         }
43         return result;
44     }
45 protected:
46     UpdatePatchWriterPtr writer_ {nullptr};
47 };
48 
49 class RowImagePatch : public ImagePatch {
50 public:
RowImagePatch(UpdatePatchWriterPtr writer)51     explicit RowImagePatch(UpdatePatchWriterPtr writer) : ImagePatch(writer) {}
~RowImagePatch()52     ~RowImagePatch() override {}
53 
54     int32_t ApplyImagePatch(const PatchParam &param, size_t &startOffset) override;
55 };
56 
57 class NormalImagePatch : public ImagePatch {
58 public:
NormalImagePatch(UpdatePatchWriterPtr writer)59     explicit NormalImagePatch(UpdatePatchWriterPtr writer) : ImagePatch(writer) {}
~NormalImagePatch()60     ~NormalImagePatch() override {}
61 
62     int32_t ApplyImagePatch(const PatchParam &param, size_t &startOffset)  override;
63 };
64 
65 class CompressedImagePatch : public ImagePatch {
66 public:
CompressedImagePatch(UpdatePatchWriterPtr writer,const std::vector<uint8_t> & bonusData)67     CompressedImagePatch(UpdatePatchWriterPtr writer, const std::vector<uint8_t> &bonusData)
68         : ImagePatch(writer), bonusData_(bonusData) {}
~CompressedImagePatch()69     ~CompressedImagePatch() override {}
70 
71     int32_t ApplyImagePatch(const PatchParam &param, size_t &startOffset) override;
72 protected:
73     virtual int32_t ReadHeader(const PatchParam &param, PatchHeader &header, size_t &offset) = 0;
74     virtual std::unique_ptr<Hpackage::FileInfo> GetFileInfo() const = 0;
75     int32_t StartReadHeader(const PatchParam &param, PatchHeader &header, size_t &offset);
76     int32_t DecompressData(Hpackage::PkgManager::PkgManagerPtr &pkgManager, Hpackage::PkgBuffer buffer,
77         Hpackage::PkgManager::StreamPtr &stream, bool memory, size_t expandedLen) const;
78 
79     std::vector<uint8_t> bonusData_ {};
80 };
81 
82 class ZipImagePatch : public CompressedImagePatch {
83 public:
ZipImagePatch(UpdatePatchWriterPtr writer,const std::vector<uint8_t> & bonusData)84     ZipImagePatch(UpdatePatchWriterPtr writer, const std::vector<uint8_t> &bonusData)
85         : CompressedImagePatch(writer, bonusData) {}
~ZipImagePatch()86     ~ZipImagePatch() override {}
87 
88 protected:
89     int32_t ReadHeader(const PatchParam &param, PatchHeader &header, size_t &offset) override;
90     std::unique_ptr<Hpackage::FileInfo> GetFileInfo() const override;
91 
92     int32_t method_ {0};
93     int32_t level_ {0};
94     int32_t windowBits_ {0};
95     int32_t memLevel_ {0};
96     int32_t strategy_ {0};
97 };
98 
99 class Lz4ImagePatch : public CompressedImagePatch {
100 public:
Lz4ImagePatch(UpdatePatchWriterPtr writer,const std::vector<uint8_t> & bonusData)101     Lz4ImagePatch(UpdatePatchWriterPtr writer, const std::vector<uint8_t> &bonusData)
102         : CompressedImagePatch(writer, bonusData) {}
~Lz4ImagePatch()103     ~Lz4ImagePatch() override {}
104 
105 protected:
106     int32_t ReadHeader(const PatchParam &param, PatchHeader &header, size_t &offset) override;
107     std::unique_ptr<Hpackage::FileInfo> GetFileInfo() const override;
108 
109     int32_t compressionLevel_ {0};
110     int32_t blockIndependence_ {0};
111     int32_t contentChecksumFlag_ {0};
112     int32_t blockSizeID_ {0};
113     int32_t method_ {0};
114     int32_t autoFlush_ {1};
115 };
116 
117 class CompressedFileRestore : public UpdatePatchWriter {
118 public:
CompressedFileRestore(Hpackage::PkgManager::FileInfoPtr fileInfo,UpdatePatchWriterPtr writer)119     CompressedFileRestore(Hpackage::PkgManager::FileInfoPtr fileInfo, UpdatePatchWriterPtr writer)
120         : UpdatePatchWriter(), fileInfo_(fileInfo), writer_(writer) {}
~CompressedFileRestore()121     ~CompressedFileRestore() override {}
122 
123     int32_t Init() override;
124     int32_t Write(size_t start, const BlockBuffer &buffer, size_t len) override;
Finish()125     int32_t Finish() override
126     {
127         return 0;
128     }
129     int32_t CompressData(size_t &originalSize, size_t &compressSize);
130 private:
131     std::vector<uint8_t> data_ {};
132     size_t dataSize_ {0};
133     Hpackage::PkgManager::FileInfoPtr fileInfo_ { nullptr };
134     UpdatePatchWriterPtr writer_ { nullptr };
135     std::unique_ptr<DeflateAdapter> deflateAdapter_ { nullptr };
136     SHA256_CTX sha256Ctx_ {};
137 };
138 } // namespace UpdatePatch
139 #endif  // IMAGE_PATCH_H
140