Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code

Delta Between Two Patch Sets: src/DefaultFileSystem.cpp

Issue 29449592: Issue 5183 - Provide async interface for FileSystem (Closed) Base URL: https://hg.adblockplus.org/libadblockplus/
Left Patch Set: Created May 26, 2017, 12:43 p.m.
Right Patch Set: Rebase on master. Last changes. Created July 7, 2017, 1:36 p.m.
Left:
Right:
Use n/p to move between diff chunks; N/P to move between comments.
Jump to:
Left: Side by side diff | Download
Right: Side by side diff | Download
« no previous file with change/comment | « libadblockplus.gyp ('k') | src/FileSystemJsObject.h » ('j') | no next file with change/comment »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
LEFTRIGHT
1 /* 1 /*
2 * This file is part of Adblock Plus <https://adblockplus.org/>, 2 * This file is part of Adblock Plus <https://adblockplus.org/>,
3 * Copyright (C) 2006-2017 eyeo GmbH 3 * Copyright (C) 2006-2017 eyeo GmbH
4 * 4 *
5 * Adblock Plus is free software: you can redistribute it and/or modify 5 * Adblock Plus is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 3 as 6 * it under the terms of the GNU General Public License version 3 as
7 * published by the Free Software Foundation. 7 * published by the Free Software Foundation.
8 * 8 *
9 * Adblock Plus is distributed in the hope that it will be useful, 9 * Adblock Plus is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details. 12 * GNU General Public License for more details.
13 * 13 *
14 * You should have received a copy of the GNU General Public License 14 * You should have received a copy of the GNU General Public License
15 * along with Adblock Plus. If not, see <http://www.gnu.org/licenses/>. 15 * along with Adblock Plus. If not, see <http://www.gnu.org/licenses/>.
16 */ 16 */
17 17
18 #include <AdblockPlus/DefaultFileSystem.h> 18 #include <AdblockPlus/DefaultFileSystem.h>
19 #include <cstdio> 19 #include <cstdio>
20 #include <cstring> 20 #include <cstring>
21 #include <fstream> 21 #include <fstream>
22 #include <sstream>
22 #include <stdexcept> 23 #include <stdexcept>
24 #include <thread>
23 25
24 #include <sys/types.h> 26 #include <sys/types.h>
25 27
26 #ifdef _WIN32 28 #ifdef _WIN32
27 #include <windows.h> 29 #include <windows.h>
28 #include <Shlobj.h> 30 #include <Shlobj.h>
29 #include <Shlwapi.h> 31 #include <Shlwapi.h>
30 #else 32 #else
31 #include <sys/stat.h> 33 #include <sys/stat.h>
32 #include <cerrno> 34 #include <cerrno>
(...skipping 26 matching lines...) Expand all
59 #else 61 #else
60 // POSIX systems: assume that file system encoding is UTF-8 and just use the 62 // POSIX systems: assume that file system encoding is UTF-8 and just use the
61 // file paths as they are. 63 // file paths as they are.
62 std::string NormalizePath(const std::string& path) 64 std::string NormalizePath(const std::string& path)
63 { 65 {
64 return path; 66 return path;
65 } 67 }
66 #endif 68 #endif
67 } 69 }
68 70
69 std::shared_ptr<std::istream> 71 IFileSystem::IOBuffer
70 DefaultFileSystem::Read(const std::string& path) const 72 DefaultFileSystemSync::Read(const std::string& path) const
71 { 73 {
72 std::shared_ptr<std::istream> result(new std::ifstream(NormalizePath(path).c_s tr())); 74 std::ifstream file(NormalizePath(path).c_str(), std::ios_base::binary);
73 if (result->fail()) 75 if (file.fail())
74 throw RuntimeErrorWithErrno("Failed to open " + path); 76 throw RuntimeErrorWithErrno("Failed to open " + path);
75 return result; 77
76 } 78 file.seekg(0, std::ios_base::end);
77 79 auto dataSize = file.tellg();
78 void DefaultFileSystem::Read(const std::string& path, 80 file.seekg(0, std::ios_base::beg);
79 const ReadCallback& callback) const 81
80 { 82 IFileSystem::IOBuffer data(dataSize);
81 try 83 file.read(reinterpret_cast<std::ifstream::char_type*>(data.data()),
82 { 84 data.size());
83 auto result = Read(path); 85 return data;
84 callback(result); 86 }
85 } 87
86 catch (...) 88 void DefaultFileSystemSync::Write(const std::string& path,
87 { 89 const IFileSystem::IOBuffer& data)
88 }
89 }
90
91 void DefaultFileSystem::Write(const std::string& path,
92 std::istream& data)
93 { 90 {
94 std::ofstream file(NormalizePath(path).c_str(), std::ios_base::out | std::ios_ base::binary); 91 std::ofstream file(NormalizePath(path).c_str(), std::ios_base::out | std::ios_ base::binary);
95 file << Utils::Slurp(data); 92 file.write(reinterpret_cast<const std::ofstream::char_type*>(data.data()),
96 } 93 data.size());
97 94 }
98 void DefaultFileSystem::Write(const std::string& path, 95
99 std::istream& data, 96 void DefaultFileSystemSync::Move(const std::string& fromPath,
100 const Callback& callback) 97 const std::string& toPath)
101 {
102 Write(path, data);
103 callback();
104 }
105
106 void DefaultFileSystem::Move(const std::string& fromPath,
107 const std::string& toPath)
108 { 98 {
109 if (rename(NormalizePath(fromPath).c_str(), NormalizePath(toPath).c_str())) 99 if (rename(NormalizePath(fromPath).c_str(), NormalizePath(toPath).c_str()))
110 throw RuntimeErrorWithErrno("Failed to move " + fromPath + " to " + toPath); 100 throw RuntimeErrorWithErrno("Failed to move " + fromPath + " to " + toPath);
111 } 101 }
112 102
113 void DefaultFileSystem::Move(const std::string& fromPath, 103 void DefaultFileSystemSync::Remove(const std::string& path)
114 const std::string& toPath,
115 const Callback& callback)
116 {
117 try
118 {
119 Move(fromPath, toPath);
120 callback();
121 }
122 catch (...)
123 {
124 }
125 }
126
127 void DefaultFileSystem::Remove(const std::string& path)
128 { 104 {
129 if (remove(NormalizePath(path).c_str())) 105 if (remove(NormalizePath(path).c_str()))
130 throw RuntimeErrorWithErrno("Failed to remove " + path); 106 throw RuntimeErrorWithErrno("Failed to remove " + path);
131 } 107 }
132 108
133 void DefaultFileSystem::Remove(const std::string& path, 109 IFileSystem::StatResult DefaultFileSystemSync::Stat(const std::string& path) con st
134 const Callback& callback) 110 {
135 { 111 IFileSystem::StatResult result;
136 try
137 {
138 Remove(path);
139 callback();
140 }
141 catch (...)
142 {
143 }
144 }
145
146 FileSystem::StatResult DefaultFileSystem::Stat(const std::string& path) const
147 {
148 FileSystem::StatResult result;
149 #ifdef WIN32 112 #ifdef WIN32
150 WIN32_FILE_ATTRIBUTE_DATA data; 113 WIN32_FILE_ATTRIBUTE_DATA data;
151 if (!GetFileAttributesExW(NormalizePath(path).c_str(), GetFileExInfoStandard, &data)) 114 if (!GetFileAttributesExW(NormalizePath(path).c_str(), GetFileExInfoStandard, &data))
152 { 115 {
153 DWORD err = GetLastError(); 116 DWORD err = GetLastError();
154 if (err == ERROR_FILE_NOT_FOUND || 117 if (err == ERROR_FILE_NOT_FOUND ||
155 err == ERROR_PATH_NOT_FOUND || 118 err == ERROR_PATH_NOT_FOUND ||
156 err == ERROR_INVALID_DRIVE) 119 err == ERROR_INVALID_DRIVE)
157 { 120 {
158 return result; 121 return result;
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
202 #if _POSIX_C_SOURCE >= 200809L 165 #if _POSIX_C_SOURCE >= 200809L
203 result.lastModified = static_cast<int64_t>(nativeStat.st_mtim.tv_sec) * MSEC_I N_SEC 166 result.lastModified = static_cast<int64_t>(nativeStat.st_mtim.tv_sec) * MSEC_I N_SEC
204 + static_cast<int64_t>(nativeStat.st_mtim.tv_nsec) / NSEC _IN_MSEC; 167 + static_cast<int64_t>(nativeStat.st_mtim.tv_nsec) / NSEC _IN_MSEC;
205 #else 168 #else
206 result.lastModified = static_cast<int64_t>(nativeStat.st_mtime) * MSEC_IN_SEC; 169 result.lastModified = static_cast<int64_t>(nativeStat.st_mtime) * MSEC_IN_SEC;
207 #endif 170 #endif
208 return result; 171 return result;
209 #endif 172 #endif
210 } 173 }
211 174
175 std::string DefaultFileSystemSync::Resolve(const std::string& path) const
176 {
177 if (basePath == "")
178 {
179 return path;
180 }
181 else
182 {
183 #ifdef _WIN32
184 if (PathIsRelative(NormalizePath(path).c_str()))
185 #else
186 if (path.length() && *path.begin() != PATH_SEPARATOR)
187 #endif
188 {
189 return basePath + PATH_SEPARATOR + path;
190 }
191 else
192 {
193 return path;
194 }
195 }
196 }
197
198 void DefaultFileSystemSync::SetBasePath(const std::string& path)
199 {
200 basePath = path;
201
202 if (*basePath.rbegin() == PATH_SEPARATOR)
203 {
204 basePath.resize(basePath.size() - 1);
205 }
206 }
207
208 DefaultFileSystem::DefaultFileSystem(const FileSystemSyncPtr& syncImpl)
209 : syncImpl(syncImpl)
210 {
211 }
212
213 void DefaultFileSystem::Read(const std::string& path,
214 const ReadCallback& callback) const
215 {
216 auto impl = syncImpl;
217 std::thread([impl, path, callback]
218 {
219 std::string error;
220 try
221 {
222 auto data = impl->Read(path);
223 callback(std::move(data), error);
224 return;
225 }
226 catch (std::exception& e)
227 {
228 error = e.what();
229 }
230 catch (...)
231 {
232 error = "Unknown error while reading from " + path;
233 }
234 callback(IOBuffer(), error);
235 }).detach();
236 }
237
238 void DefaultFileSystem::Write(const std::string& path,
239 const IOBuffer& data,
240 const Callback& callback)
241 {
242 auto impl = syncImpl;
243 std::thread([impl, path, data, callback]
244 {
245 std::string error;
246 try
247 {
248 impl->Write(path, data);
249 }
250 catch (std::exception& e)
251 {
252 error = e.what();
253 }
254 catch (...)
255 {
256 error = "Unknown error while writing to " + path;
257 }
258 callback(error);
259 }).detach();
260 }
261
262 void DefaultFileSystem::Move(const std::string& fromPath,
263 const std::string& toPath,
264 const Callback& callback)
265 {
266 auto impl = syncImpl;
267 std::thread([impl, fromPath, toPath, callback]
268 {
269 std::string error;
270 try
271 {
272 impl->Move(fromPath, toPath);
273 }
274 catch (std::exception& e)
275 {
276 error = e.what();
277 }
278 catch (...)
279 {
280 error = "Unknown error while moving " + fromPath + " to " + toPath;
281 }
282 callback(error);
283 }).detach();
284 }
285
286 void DefaultFileSystem::Remove(const std::string& path,
287 const Callback& callback)
288 {
289 auto impl = syncImpl;
290 std::thread([impl, path, callback]
291 {
292 std::string error;
293 try
294 {
295 impl->Remove(path);
296 }
297 catch (std::exception& e)
298 {
299 error = e.what();
300 }
301 catch (...)
302 {
303 error = "Unknown error while removing " + path;
304 }
305 callback(error);
306 }).detach();
307 }
308
212 void DefaultFileSystem::Stat(const std::string& path, 309 void DefaultFileSystem::Stat(const std::string& path,
213 const StatCallback& callback) const 310 const StatCallback& callback) const
214 { 311 {
215 try 312 auto impl = syncImpl;
216 { 313 std::thread([impl, path, callback]
217 auto stats = Stat(path); 314 {
218 callback(stats); 315 std::string error;
219 } 316 try
220 catch (...) 317 {
221 { 318 auto result = impl->Stat(path);
222 } 319 callback(result, error);
320 return;
321 }
322 catch (std::exception& e)
323 {
324 error = e.what();
325 }
326 catch (...)
327 {
328 error = "Unknown error while calling stat on " + path;
329 }
330 callback(StatResult(), error);
331 }).detach();
223 } 332 }
224 333
225 std::string DefaultFileSystem::Resolve(const std::string& path) const 334 std::string DefaultFileSystem::Resolve(const std::string& path) const
226 { 335 {
227 if (basePath == "") 336 return syncImpl->Resolve(path);
228 { 337 }
229 return path;
230 }
231 else
232 {
233 #ifdef _WIN32
234 if (PathIsRelative(NormalizePath(path).c_str()))
235 #else
236 if (path.length() && *path.begin() != PATH_SEPARATOR)
237 #endif
238 {
239 return basePath + PATH_SEPARATOR + path;
240 }
241 else
242 {
243 return path;
244 }
245 }
246 }
247 void DefaultFileSystem::Resolve(const std::string& path,
248 const ResolveCallback& callback) const
249 {
250 callback(Resolve(path));
251 }
252
253 void DefaultFileSystem::SetBasePath(const std::string& path)
254 {
255 basePath = path;
256
257 if (*basePath.rbegin() == PATH_SEPARATOR)
258 {
259 basePath.resize(basePath.size() - 1);
260 }
261 }
262
LEFTRIGHT

Powered by Google App Engine
This is Rietveld