- while ((n = read(from_fd, buf, sizeof(buf))) > 0)
- if (write(to_fd, buf, n) != n) {
- error(to_name);
- bad(to_name);
+ /*
+ * Mmap and write if less than 8M (the limit is so we don't totally
+ * trash memory on big files. This is really a minor hack, but it
+ * wins some CPU back.
+ */
+ if (size <= 8 * 1048576) {
+ if ((p = mmap(NULL, (size_t)size, PROT_READ,
+ 0, from_fd, (off_t)0)) == (char *)-1)
+ err("%s: %s", from_name, strerror(errno));
+ if (write(to_fd, p, size) != size)
+ err("%s: %s", to_name, strerror(errno));
+ } else {
+ while ((nr = read(from_fd, buf, sizeof(buf))) > 0)
+ if ((nw = write(to_fd, buf, nr)) != nr) {
+ serrno = errno;
+ (void)unlink(to_name);
+ err("%s: %s",
+ to_name, strerror(nw > 0 ? EIO : serrno));
+ }
+ if (nr != 0) {
+ serrno = errno;
+ (void)unlink(to_name);
+ err("%s: %s", from_name, strerror(serrno));