summaryrefslogtreecommitdiff
path: root/copy.c
diff options
context:
space:
mode:
Diffstat (limited to 'copy.c')
-rw-r--r--copy.c36
1 files changed, 36 insertions, 0 deletions
diff --git a/copy.c b/copy.c
new file mode 100644
index 0000000000..c225d1b0ff
--- /dev/null
+++ b/copy.c
@@ -0,0 +1,36 @@
+#include "cache.h"
+
+int copy_fd(int ifd, int ofd)
+{
+ while (1) {
+ char buffer[8192];
+ char *buf = buffer;
+ ssize_t len = xread(ifd, buffer, sizeof(buffer));
+ if (!len)
+ break;
+ if (len < 0) {
+ int read_error;
+ read_error = errno;
+ close(ifd);
+ return error("copy-fd: read returned %s",
+ strerror(read_error));
+ }
+ while (len) {
+ int written = xwrite(ofd, buf, len);
+ if (written > 0) {
+ buf += written;
+ len -= written;
+ }
+ else if (!written) {
+ close(ifd);
+ return error("copy-fd: write returned 0");
+ } else {
+ close(ifd);
+ return error("copy-fd: write returned %s",
+ strerror(errno));
+ }
+ }
+ }
+ close(ifd);
+ return 0;
+}