Switch FileWriter::Write to boolean result code.
FileWriter::Write returned either the number of bytes written, or a negative
error code. No clients were doing anything with the result other than checking
for success or failure, and many clients were considering any non-zero result
success.
So, I changed the API to return less information, but just the information the
clients needed. Success or failure.
BUG=chromium-os:8521
TEST=Unittests
Change-Id: I51513d6aa7b704dc27fb90d5fae4dc7118a3f86c
Reviewed-on: https://gerrit.chromium.org/gerrit/11532
Reviewed-by: Andrew de los Reyes <[email protected]>
Tested-by: Don Garrett <[email protected]>
Commit-Ready: Don Garrett <[email protected]>
diff --git a/delta_diff_generator.cc b/delta_diff_generator.cc
index 1c962f1..cc8f352 100644
--- a/delta_diff_generator.cc
+++ b/delta_diff_generator.cc
@@ -337,8 +337,7 @@
// Returns true on success.
bool WriteUint64AsBigEndian(FileWriter* writer, const uint64_t value) {
uint64_t value_be = htobe64(value);
- TEST_AND_RETURN_FALSE(writer->Write(&value_be, sizeof(value_be)) ==
- sizeof(value_be));
+ TEST_AND_RETURN_FALSE(writer->Write(&value_be, sizeof(value_be)));
return true;
}
@@ -1163,8 +1162,7 @@
TEST_AND_RETURN_FALSE(rc == static_cast<ssize_t>(buf.size()));
op->set_data_offset(out_file_size);
- TEST_AND_RETURN_FALSE(writer.Write(&buf[0], buf.size()) ==
- static_cast<ssize_t>(buf.size()));
+ TEST_AND_RETURN_FALSE(writer.Write(&buf[0], buf.size()));
out_file_size += buf.size();
}
return true;
@@ -1486,8 +1484,7 @@
ScopedFileWriterCloser writer_closer(&writer);
// Write header
- TEST_AND_RETURN_FALSE(writer.Write(kDeltaMagic, strlen(kDeltaMagic)) ==
- static_cast<ssize_t>(strlen(kDeltaMagic)));
+ TEST_AND_RETURN_FALSE(writer.Write(kDeltaMagic, strlen(kDeltaMagic)));
// Write version number
TEST_AND_RETURN_FALSE(WriteUint64AsBigEndian(&writer, kVersionNumber));
@@ -1500,8 +1497,7 @@
LOG(INFO) << "Writing final delta file protobuf... "
<< serialized_manifest.size();
TEST_AND_RETURN_FALSE(writer.Write(serialized_manifest.data(),
- serialized_manifest.size()) ==
- static_cast<ssize_t>(serialized_manifest.size()));
+ serialized_manifest.size()));
// Append the data blobs
LOG(INFO) << "Writing final delta file data blobs...";
@@ -1516,7 +1512,7 @@
break;
}
TEST_AND_RETURN_FALSE_ERRNO(rc > 0);
- TEST_AND_RETURN_FALSE(writer.Write(buf, rc) == rc);
+ TEST_AND_RETURN_FALSE(writer.Write(buf, rc));
}
// Write signature blob.
@@ -1528,8 +1524,7 @@
vector<string>(1, private_key_path),
&signature_blob));
TEST_AND_RETURN_FALSE(writer.Write(&signature_blob[0],
- signature_blob.size()) ==
- static_cast<ssize_t>(signature_blob.size()));
+ signature_blob.size()));
}
int64_t manifest_metadata_size =
diff --git a/delta_performer.cc b/delta_performer.cc
index 0e49df7..66c23d4 100644
--- a/delta_performer.cc
+++ b/delta_performer.cc
@@ -232,11 +232,9 @@
}
-// Wrapper around write. Returns bytes written on success or
-// -errno on error.
-// This function performs as many actions as it can, given the amount of
-// data received thus far.
-ssize_t DeltaPerformer::Write(const void* bytes, size_t count) {
+// Wrapper around write. Returns true if all requested bytes
+// were written, or false on any error, reguardless of progress.
+bool DeltaPerformer::Write(const void* bytes, size_t count) {
const char* c_bytes = reinterpret_cast<const char*>(bytes);
buffer_.insert(buffer_.end(), c_bytes, c_bytes + count);
@@ -245,10 +243,10 @@
&manifest_,
&manifest_metadata_size_);
if (result == kMetadataParseError) {
- return -EINVAL;
+ return false;
}
if (result == kMetadataParseInsufficientData) {
- return count;
+ return true;
}
// Remove protobuf and header info from buffer_, so buffer_ contains
// just data blobs
@@ -260,7 +258,7 @@
LogPartitionInfo(manifest_);
if (!PrimeUpdateState()) {
LOG(ERROR) << "Unable to prime the update state.";
- return -EINVAL;
+ return false;
}
}
ssize_t total_operations = manifest_.install_operations_size() +
@@ -289,25 +287,25 @@
if (!PerformReplaceOperation(op, is_kernel_partition)) {
LOG(ERROR) << "Failed to perform replace operation "
<< next_operation_num_;
- return -EINVAL;
+ return false;
}
} else if (op.type() == DeltaArchiveManifest_InstallOperation_Type_MOVE) {
if (!PerformMoveOperation(op, is_kernel_partition)) {
LOG(ERROR) << "Failed to perform move operation "
<< next_operation_num_;
- return -EINVAL;
+ return false;
}
} else if (op.type() == DeltaArchiveManifest_InstallOperation_Type_BSDIFF) {
if (!PerformBsdiffOperation(op, is_kernel_partition)) {
LOG(ERROR) << "Failed to perform bsdiff operation "
<< next_operation_num_;
- return -EINVAL;
+ return false;
}
}
next_operation_num_++;
CheckpointUpdateProgress();
}
- return count;
+ return true;
}
bool DeltaPerformer::CanPerformInstallOperation(
diff --git a/delta_performer.h b/delta_performer.h
index 5c1f3ab..dd8f8d8 100644
--- a/delta_performer.h
+++ b/delta_performer.h
@@ -52,9 +52,9 @@
// Open()ed again.
int Open(const char* path, int flags, mode_t mode);
- // Wrapper around write. Returns bytes written on success or
- // -errno on error.
- ssize_t Write(const void* bytes, size_t count);
+ // Wrapper around write. Returns true if all requested bytes
+ // were written, or false on any error, reguardless of progress.
+ bool Write(const void* bytes, size_t count);
// Wrapper around close. Returns 0 on success or -errno on error.
// Closes both 'path' given to Open() and the kernel path.
diff --git a/delta_performer_unittest.cc b/delta_performer_unittest.cc
index 0983cd3..b820ab8 100644
--- a/delta_performer_unittest.cc
+++ b/delta_performer_unittest.cc
@@ -484,7 +484,7 @@
const size_t kBytesPerWrite = 5;
for (size_t i = 0; i < delta.size(); i += kBytesPerWrite) {
size_t count = min(delta.size() - i, kBytesPerWrite);
- EXPECT_EQ(count, performer.Write(&delta[i], count));
+ EXPECT_TRUE(performer.Write(&delta[i], count));
}
// Wrapper around close. Returns 0 on success or -errno on error.
@@ -586,9 +586,9 @@
DeltaPerformer performer(&prefs);
EXPECT_EQ(0, performer.Open("/dev/null", 0, 0));
EXPECT_TRUE(performer.OpenKernel("/dev/null"));
- EXPECT_EQ(4, performer.Write("junk", 4));
- EXPECT_EQ(8, performer.Write("morejunk", 8));
- EXPECT_LT(performer.Write("morejunk", 8), 0);
+ EXPECT_TRUE(performer.Write("junk", 4));
+ EXPECT_TRUE(performer.Write("morejunk", 8));
+ EXPECT_FALSE(performer.Write("morejunk", 8));
EXPECT_LT(performer.Close(), 0);
}
diff --git a/download_action.cc b/download_action.cc
index 989625d..b08c1fc 100644
--- a/download_action.cc
+++ b/download_action.cc
@@ -96,7 +96,7 @@
bytes_received_ += length;
if (delegate_)
delegate_->BytesReceived(bytes_received_, install_plan_.size);
- if (writer_ && writer_->Write(bytes, length) < 0) {
+ if (writer_ && !writer_->Write(bytes, length)) {
LOG(ERROR) << "Write error -- terminating processing.";
// Don't tell the action processor that the action is complete until we get
// the TransferTerminated callback. Otherwise, this and the HTTP fetcher
diff --git a/download_action_unittest.cc b/download_action_unittest.cc
index bf12326..799d8af 100644
--- a/download_action_unittest.cc
+++ b/download_action_unittest.cc
@@ -81,9 +81,9 @@
TestDirectFileWriter() : fail_write_(0), current_write_(0) {}
void set_fail_write(int fail_write) { fail_write_ = fail_write; }
- virtual ssize_t Write(const void* bytes, size_t count) {
+ virtual bool Write(const void* bytes, size_t count) {
if (++current_write_ == fail_write_) {
- return -EINVAL;
+ return false;
}
return DirectFileWriter::Write(bytes, count);
}
diff --git a/file_writer.cc b/file_writer.cc
index 1a95a75..ad29844 100644
--- a/file_writer.cc
+++ b/file_writer.cc
@@ -15,7 +15,7 @@
return 0;
}
-ssize_t DirectFileWriter::Write(const void* bytes, size_t count) {
+bool DirectFileWriter::Write(const void* bytes, size_t count) {
CHECK_GE(fd_, 0);
const char* char_bytes = reinterpret_cast<const char*>(bytes);
@@ -24,11 +24,11 @@
ssize_t rc = write(fd_, char_bytes + bytes_written,
count - bytes_written);
if (rc < 0)
- return -errno;
+ return false;
bytes_written += rc;
}
CHECK_EQ(bytes_written, count);
- return bytes_written;
+ return bytes_written == count;
}
int DirectFileWriter::Close() {
diff --git a/file_writer.h b/file_writer.h
index a534b96..5fd4c5a 100644
--- a/file_writer.h
+++ b/file_writer.h
@@ -27,9 +27,9 @@
// Wrapper around open. Returns 0 on success or -errno on error.
virtual int Open(const char* path, int flags, mode_t mode) = 0;
- // Wrapper around write. Returns bytes written on success or
- // -errno on error.
- virtual ssize_t Write(const void* bytes, size_t count) = 0;
+ // Wrapper around write. Returns true if all requested bytes
+ // were written, or false on any error, reguardless of progress.
+ virtual bool Write(const void* bytes, size_t count) = 0;
// Wrapper around close. Returns 0 on success or -errno on error.
virtual int Close() = 0;
@@ -47,7 +47,7 @@
virtual ~DirectFileWriter() {}
virtual int Open(const char* path, int flags, mode_t mode);
- virtual ssize_t Write(const void* bytes, size_t count);
+ virtual bool Write(const void* bytes, size_t count);
virtual int Close();
int fd() const { return fd_; }
diff --git a/file_writer_unittest.cc b/file_writer_unittest.cc
index 6e494ec..1b7b1e6 100644
--- a/file_writer_unittest.cc
+++ b/file_writer_unittest.cc
@@ -22,10 +22,10 @@
TEST(FileWriterTest, SimpleTest) {
DirectFileWriter file_writer;
const string path("/tmp/FileWriterTest");
- ASSERT_EQ(0, file_writer.Open(path.c_str(),
+ EXPECT_EQ(0, file_writer.Open(path.c_str(),
O_CREAT | O_LARGEFILE | O_TRUNC | O_WRONLY,
0644));
- ASSERT_EQ(4, file_writer.Write("test", 4));
+ EXPECT_TRUE(file_writer.Write("test", 4));
vector<char> actual_data;
EXPECT_TRUE(utils::ReadFile(path, &actual_data));
@@ -47,7 +47,7 @@
EXPECT_EQ(0, file_writer.Open(path.c_str(),
O_CREAT | O_LARGEFILE | O_TRUNC | O_RDONLY,
0644));
- EXPECT_EQ(-EBADF, file_writer.Write("x", 1));
+ EXPECT_FALSE(file_writer.Write("x", 1));
EXPECT_EQ(0, file_writer.Close());
}
diff --git a/utils.cc b/utils.cc
index 5273347..1c9425a 100644
--- a/utils.cc
+++ b/utils.cc
@@ -89,7 +89,7 @@
O_WRONLY | O_CREAT | O_TRUNC,
0600));
ScopedFileWriterCloser closer(&writer);
- TEST_AND_RETURN_FALSE_ERRNO(data_len == writer.Write(data, data_len));
+ TEST_AND_RETURN_FALSE_ERRNO(writer.Write(data, data_len));
return true;
}