|
56 | 56 | #include <android-base/macros.h> |
57 | 57 | #include "absl/strings/str_join.h" |
58 | 58 | #include "absl/strings/str_split.h" |
59 | | -#include <android-base/unique_fd.h> |
60 | 59 | #include "absl/log/check.h" |
61 | 60 | #include "absl/log/log.h" |
62 | 61 | #include "absl/strings/match.h" |
@@ -344,81 +343,57 @@ Result<void> RecursivelyRemoveDirectory(const std::string& path) { |
344 | 343 |
|
345 | 344 | namespace { |
346 | 345 |
|
347 | | -bool SendFile(int out_fd, int in_fd, off64_t* offset, size_t count) { |
348 | | - while (count > 0) { |
349 | | -#ifdef __linux__ |
350 | | - const auto bytes_written = |
351 | | - TEMP_FAILURE_RETRY(sendfile(out_fd, in_fd, offset, count)); |
352 | | - if (bytes_written <= 0) { |
353 | | - return false; |
354 | | - } |
355 | | -#elif defined(__APPLE__) |
356 | | - off_t bytes_written = count; |
357 | | - auto success = TEMP_FAILURE_RETRY( |
358 | | - sendfile(in_fd, out_fd, *offset, &bytes_written, nullptr, 0)); |
359 | | - *offset += bytes_written; |
360 | | - if (success < 0 || bytes_written == 0) { |
361 | | - return false; |
362 | | - } |
363 | | -#endif |
364 | | - count -= bytes_written; |
365 | | - } |
366 | | - return true; |
367 | | -} |
368 | | - |
369 | 346 | } // namespace |
370 | 347 |
|
371 | 348 | bool Copy(const std::string& from, const std::string& to) { |
372 | | - android::base::unique_fd fd_from( |
373 | | - open(from.c_str(), O_RDONLY | O_CLOEXEC)); |
374 | | - android::base::unique_fd fd_to( |
375 | | - open(to.c_str(), O_WRONLY | O_CREAT | O_TRUNC | O_CLOEXEC, 0644)); |
| 349 | + SharedFD fd_from = SharedFD::Open(from, O_RDONLY); |
| 350 | + SharedFD fd_to = SharedFD::Open(to, O_WRONLY | O_CREAT | O_TRUNC, 0644); |
376 | 351 |
|
377 | | - if (fd_from.get() < 0 || fd_to.get() < 0) { |
| 352 | + if (!fd_from->IsOpen() || !fd_to->IsOpen()) { |
378 | 353 | return false; |
379 | 354 | } |
380 | 355 |
|
381 | | - off_t farthest_seek = lseek(fd_from.get(), 0, SEEK_END); |
| 356 | + off_t farthest_seek = fd_from->LSeek(0, SEEK_END); |
382 | 357 | if (farthest_seek == -1) { |
383 | | - PLOG(ERROR) << "Could not lseek in \"" << from << "\""; |
| 358 | + LOG(ERROR) << "Could not lseek in \"" << from |
| 359 | + << "\": " << fd_from->StrError(); |
384 | 360 | return false; |
385 | 361 | } |
386 | | - if (ftruncate64(fd_to.get(), farthest_seek) < 0) { |
387 | | - PLOG(ERROR) << "Failed to ftruncate " << to; |
| 362 | + if (fd_to->Truncate(farthest_seek) < 0) { |
| 363 | + LOG(ERROR) << "Failed to truncate " << to << ": " << fd_to->StrError(); |
388 | 364 | } |
389 | 365 | off_t offset = 0; |
390 | 366 | while (offset < farthest_seek) { |
391 | | - off_t new_offset = lseek(fd_from.get(), offset, SEEK_HOLE); |
| 367 | + off_t new_offset = fd_from->LSeek(offset, SEEK_HOLE); |
392 | 368 | if (new_offset == -1) { |
393 | | - // ENXIO is returned when there are no more blocks of this type |
394 | | - // coming. |
395 | | - if (errno == ENXIO) { |
| 369 | + if (fd_from->GetErrno() == ENXIO) { |
396 | 370 | return true; |
397 | 371 | } |
398 | | - PLOG(ERROR) << "Could not lseek in \"" << from << "\""; |
| 372 | + LOG(ERROR) << "Could not lseek in \"" << from |
| 373 | + << "\": " << fd_from->StrError(); |
399 | 374 | return false; |
400 | 375 | } |
401 | 376 | auto data_bytes = new_offset - offset; |
402 | | - if (lseek(fd_to.get(), offset, SEEK_SET) < 0) { |
403 | | - PLOG(ERROR) << "lseek() on " << to << " failed"; |
| 377 | + if (fd_to->LSeek(offset, SEEK_SET) < 0) { |
| 378 | + LOG(ERROR) << "lseek() on " << to << " failed: " << fd_to->StrError(); |
404 | 379 | return false; |
405 | 380 | } |
406 | | - if (!SendFile(fd_to.get(), fd_from.get(), &offset, data_bytes)) { |
407 | | - PLOG(ERROR) << "sendfile() failed"; |
| 381 | + if (!fd_to->SendFile(*fd_from, &offset, data_bytes)) { |
| 382 | + LOG(ERROR) << "SendFile failed: " << fd_to->StrError(); |
408 | 383 | return false; |
409 | 384 | } |
410 | 385 | CHECK_EQ(offset, new_offset); |
| 386 | + |
411 | 387 | if (offset >= farthest_seek) { |
412 | 388 | return true; |
413 | 389 | } |
414 | | - new_offset = lseek(fd_from.get(), offset, SEEK_DATA); |
| 390 | + new_offset = fd_from->LSeek(offset, SEEK_DATA); |
415 | 391 | if (new_offset == -1) { |
416 | | - // ENXIO is returned when there are no more blocks of this type |
417 | | - // coming. |
418 | | - if (errno == ENXIO) { |
| 392 | + if (fd_from->GetErrno() == ENXIO) { |
419 | 393 | return true; |
420 | 394 | } |
421 | | - PLOG(ERROR) << "Could not lseek in \"" << from << "\""; |
| 395 | + LOG(ERROR) << "Could not lseek in \"" << from |
| 396 | + << "\": " << fd_from->StrError(); |
422 | 397 | return false; |
423 | 398 | } |
424 | 399 | offset = new_offset; |
|
0 commit comments