blob: db91a77a5ae6dd2561d240874ea2a090721f3c68 [file] [log] [blame]
Adam Lesinskia40e9722015-11-24 19:11:46 -08001/*
2 * Copyright (C) 2015 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef AAPT_IO_DATA_H
18#define AAPT_IO_DATA_H
19
Adam Lesinskicacb28f2016-10-19 12:18:14 -070020#include <memory>
Adam Lesinskia40e9722015-11-24 19:11:46 -080021
Adam Lesinskice5e56e2016-10-21 17:56:45 -070022#include "android-base/macros.h"
23#include "utils/FileMap.h"
24
Adam Lesinski06460ef2017-03-14 18:52:13 -070025#include "io/Io.h"
26
Adam Lesinskia40e9722015-11-24 19:11:46 -080027namespace aapt {
28namespace io {
29
Adam Lesinski06460ef2017-03-14 18:52:13 -070030// Interface for a block of contiguous memory. An instance of this interface owns the data.
Adam Lesinski00451162017-10-03 07:44:08 -070031class IData : public KnownSizeInputStream {
Adam Lesinskicacb28f2016-10-19 12:18:14 -070032 public:
33 virtual ~IData() = default;
Adam Lesinskia40e9722015-11-24 19:11:46 -080034
Adam Lesinskicacb28f2016-10-19 12:18:14 -070035 virtual const void* data() const = 0;
36 virtual size_t size() const = 0;
Adam Lesinski00451162017-10-03 07:44:08 -070037
38 virtual size_t TotalSize() const override {
39 return size();
40 }
Adam Lesinskia40e9722015-11-24 19:11:46 -080041};
42
Adam Lesinski5eeaadd2016-08-25 12:26:56 -070043class DataSegment : public IData {
Adam Lesinskicacb28f2016-10-19 12:18:14 -070044 public:
45 explicit DataSegment(std::unique_ptr<IData> data, size_t offset, size_t len)
Adam Lesinski06460ef2017-03-14 18:52:13 -070046 : data_(std::move(data)), offset_(offset), len_(len), next_read_(offset) {}
47 virtual ~DataSegment() = default;
Adam Lesinski5eeaadd2016-08-25 12:26:56 -070048
Adam Lesinskicacb28f2016-10-19 12:18:14 -070049 const void* data() const override {
Adam Lesinskice5e56e2016-10-21 17:56:45 -070050 return static_cast<const uint8_t*>(data_->data()) + offset_;
Adam Lesinskicacb28f2016-10-19 12:18:14 -070051 }
Adam Lesinski5eeaadd2016-08-25 12:26:56 -070052
Adam Lesinskice5e56e2016-10-21 17:56:45 -070053 size_t size() const override { return len_; }
Adam Lesinski5eeaadd2016-08-25 12:26:56 -070054
Adam Lesinski06460ef2017-03-14 18:52:13 -070055 bool Next(const void** data, size_t* size) override {
56 if (next_read_ == offset_ + len_) {
57 return false;
58 }
59 *data = static_cast<const uint8_t*>(data_->data()) + next_read_;
60 *size = len_ - (next_read_ - offset_);
61 next_read_ = offset_ + len_;
62 return true;
63 }
64
65 void BackUp(size_t count) override {
66 if (count > next_read_ - offset_) {
67 next_read_ = offset_;
68 } else {
69 next_read_ -= count;
70 }
71 }
72
73 bool CanRewind() const override { return true; }
74
75 bool Rewind() override {
76 next_read_ = offset_;
77 return true;
78 }
79
80 size_t ByteCount() const override { return next_read_ - offset_; }
81
82 bool HadError() const override { return false; }
83
Adam Lesinskicacb28f2016-10-19 12:18:14 -070084 private:
85 DISALLOW_COPY_AND_ASSIGN(DataSegment);
Adam Lesinski5eeaadd2016-08-25 12:26:56 -070086
Adam Lesinskice5e56e2016-10-21 17:56:45 -070087 std::unique_ptr<IData> data_;
88 size_t offset_;
89 size_t len_;
Adam Lesinski06460ef2017-03-14 18:52:13 -070090 size_t next_read_;
Adam Lesinski5eeaadd2016-08-25 12:26:56 -070091};
92
Adam Lesinski06460ef2017-03-14 18:52:13 -070093// Implementation of IData that exposes a memory mapped file.
94// The mmapped file is owned by this object.
Adam Lesinskia40e9722015-11-24 19:11:46 -080095class MmappedData : public IData {
Adam Lesinskicacb28f2016-10-19 12:18:14 -070096 public:
Adam Lesinski06460ef2017-03-14 18:52:13 -070097 explicit MmappedData(android::FileMap&& map) : map_(std::forward<android::FileMap>(map)) {}
98 virtual ~MmappedData() = default;
Adam Lesinskia40e9722015-11-24 19:11:46 -080099
Adam Lesinskice5e56e2016-10-21 17:56:45 -0700100 const void* data() const override { return map_.getDataPtr(); }
Adam Lesinskia40e9722015-11-24 19:11:46 -0800101
Adam Lesinskice5e56e2016-10-21 17:56:45 -0700102 size_t size() const override { return map_.getDataLength(); }
Adam Lesinskia40e9722015-11-24 19:11:46 -0800103
Adam Lesinski06460ef2017-03-14 18:52:13 -0700104 bool Next(const void** data, size_t* size) override {
105 if (next_read_ == map_.getDataLength()) {
106 return false;
107 }
108 *data = reinterpret_cast<const uint8_t*>(map_.getDataPtr()) + next_read_;
109 *size = map_.getDataLength() - next_read_;
110 next_read_ = map_.getDataLength();
111 return true;
112 }
113
114 void BackUp(size_t count) override {
115 if (count > next_read_) {
116 next_read_ = 0;
117 } else {
118 next_read_ -= count;
119 }
120 }
121
122 bool CanRewind() const override { return true; }
123
124 bool Rewind() override {
125 next_read_ = 0;
126 return true;
127 }
128
129 size_t ByteCount() const override { return next_read_; }
130
131 bool HadError() const override { return false; }
132
Adam Lesinskicacb28f2016-10-19 12:18:14 -0700133 private:
Adam Lesinski06460ef2017-03-14 18:52:13 -0700134 DISALLOW_COPY_AND_ASSIGN(MmappedData);
135
Adam Lesinskice5e56e2016-10-21 17:56:45 -0700136 android::FileMap map_;
Adam Lesinski06460ef2017-03-14 18:52:13 -0700137 size_t next_read_ = 0;
Adam Lesinskia40e9722015-11-24 19:11:46 -0800138};
139
Adam Lesinski06460ef2017-03-14 18:52:13 -0700140// Implementation of IData that exposes a block of memory that was malloc'ed (new'ed).
141// The memory is owned by this object.
Adam Lesinskia40e9722015-11-24 19:11:46 -0800142class MallocData : public IData {
Adam Lesinskicacb28f2016-10-19 12:18:14 -0700143 public:
144 MallocData(std::unique_ptr<const uint8_t[]> data, size_t size)
Adam Lesinskice5e56e2016-10-21 17:56:45 -0700145 : data_(std::move(data)), size_(size) {}
Adam Lesinski06460ef2017-03-14 18:52:13 -0700146 virtual ~MallocData() = default;
Adam Lesinskia40e9722015-11-24 19:11:46 -0800147
Adam Lesinskice5e56e2016-10-21 17:56:45 -0700148 const void* data() const override { return data_.get(); }
Adam Lesinskia40e9722015-11-24 19:11:46 -0800149
Adam Lesinskice5e56e2016-10-21 17:56:45 -0700150 size_t size() const override { return size_; }
Adam Lesinskia40e9722015-11-24 19:11:46 -0800151
Adam Lesinski06460ef2017-03-14 18:52:13 -0700152 bool Next(const void** data, size_t* size) override {
153 if (next_read_ == size_) {
154 return false;
155 }
156 *data = data_.get() + next_read_;
157 *size = size_ - next_read_;
158 next_read_ = size_;
159 return true;
160 }
161
162 void BackUp(size_t count) override {
163 if (count > next_read_) {
164 next_read_ = 0;
165 } else {
166 next_read_ -= count;
167 }
168 }
169
170 bool CanRewind() const override { return true; }
171
172 bool Rewind() override {
173 next_read_ = 0;
174 return true;
175 }
176
177 size_t ByteCount() const override { return next_read_; }
178
179 bool HadError() const override { return false; }
180
Adam Lesinskicacb28f2016-10-19 12:18:14 -0700181 private:
Adam Lesinski06460ef2017-03-14 18:52:13 -0700182 DISALLOW_COPY_AND_ASSIGN(MallocData);
183
Adam Lesinskice5e56e2016-10-21 17:56:45 -0700184 std::unique_ptr<const uint8_t[]> data_;
185 size_t size_;
Adam Lesinski06460ef2017-03-14 18:52:13 -0700186 size_t next_read_ = 0;
Adam Lesinskia40e9722015-11-24 19:11:46 -0800187};
188
Adam Lesinski06460ef2017-03-14 18:52:13 -0700189// When mmap fails because the file has length 0, we use the EmptyData to simulate data of length 0.
Adam Lesinski52364f72016-01-11 13:10:24 -0800190class EmptyData : public IData {
Adam Lesinskicacb28f2016-10-19 12:18:14 -0700191 public:
Adam Lesinski06460ef2017-03-14 18:52:13 -0700192 virtual ~EmptyData() = default;
193
Adam Lesinskicacb28f2016-10-19 12:18:14 -0700194 const void* data() const override {
195 static const uint8_t d = 0;
196 return &d;
197 }
Adam Lesinski52364f72016-01-11 13:10:24 -0800198
Adam Lesinskicacb28f2016-10-19 12:18:14 -0700199 size_t size() const override { return 0u; }
Adam Lesinski06460ef2017-03-14 18:52:13 -0700200
201 bool Next(const void** /*data*/, size_t* /*size*/) override { return false; }
202
203 void BackUp(size_t /*count*/) override {}
204
205 bool CanRewind() const override { return true; }
206
207 bool Rewind() override { return true; }
208
209 size_t ByteCount() const override { return 0u; }
210
211 bool HadError() const override { return false; }
Adam Lesinski52364f72016-01-11 13:10:24 -0800212};
213
Adam Lesinskicacb28f2016-10-19 12:18:14 -0700214} // namespace io
215} // namespace aapt
Adam Lesinskia40e9722015-11-24 19:11:46 -0800216
217#endif /* AAPT_IO_DATA_H */