// // aegis - project change supervisor // Copyright (C) 2001-2006, 2008 Peter Miller // // This program is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation; either version 3 of the License, or // (at your option) any later version. // // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program. If not, see // . // #include #include #include #include #include #include #include // // NAME // copyfile - copy a file // // SYNOPSIS // int copyfile(char *src, char *dst); // // DESCRIPTION // The copyfile function complements the link and rename functions. // // ARGUMENTS // src - pathname of source file // dst - pathname of destination file // // RETURNS // 0 on success // -1 on error, setting errno appropriately // int copyfile(const char *src, const char *dst) { int src_fd; int dst_fd; char *buffer; long max; long nbytes; long nbytes2; int err; int result; trace(("copyfile(\"%s\", \"%s\")\n{\n", src, dst)); os_interrupt_cope(); result = -1; src_fd = open(src, O_RDONLY, 0666); if (src_fd < 0) goto done; dst_fd = open(dst, O_WRONLY | O_CREAT | O_TRUNC, 0666); if (dst_fd < 0) { err = errno; close(src_fd); errno = err; goto done; } max = 1L << 13; errno = 0; buffer = (char *)malloc(max); if (!buffer) { err = errno ? errno : ENOMEM; close(dst_fd); close(src_fd); errno = err; goto done; } for (;;) { nbytes = read(src_fd, buffer, max); if (nbytes < 0) { err = errno; close(src_fd); close(dst_fd); free(buffer); errno = err; goto done; } if (nbytes == 0) break; nbytes2 = write(dst_fd, buffer, nbytes); if (nbytes2 < 0) { err = errno; close(src_fd); close(dst_fd); free(buffer); errno = err; goto done; } if (nbytes2 != nbytes) { close(src_fd); close(dst_fd); free(buffer); errno = EIO; // weird device, probably goto done; } } free(buffer); if (close(src_fd)) { err = errno; close(dst_fd); errno = err; goto done; } result = close(dst_fd); // // here for all exits // done: trace(("return %d; /* errno = %d */\n", result, errno)); trace(("}\n")); return result; }