#c #linux #copy #move #disk-partitioning
#c #linux #Копировать #переместить #разделение диска
Вопрос:
rename (), link() не работают
Спасибо!
Комментарии:
1.
fopen
fread
fwrite
fclose
. Разные разделы означают, что вы должны копировать.
Ответ №1:
Вы пробовали использовать стандартные старые функции C?
`fopen` the source on one partition
`fopen` the destination on the other partition
LOOP while `fread` > 0
`fread` from the source to a buff
`fwrite` to the dest from a buff
А затем закройте ваши файлы (т.Е. fclose
).
Это также более переносимо.
РЕДАКТИРОВАТЬ: если вы хотели, чтобы это было действительно просто, почему бы просто не использовать язык сценариев (python / bash) и сделать это в нескольких строках.
Комментарии:
1. особенно легко с чем-то вроде
shutil.copy()
2. «Это также более переносимо» — вроде того. Проблема с установкой на реализацию «переносимой копии файла» заключается в том, что разные системы имеют разные метаданные файла, начиная с прав доступа к файлам и заканчивая временем доступа, правами собственности, списками ACL и дополнительными потоками данных. Таким образом, полученная копия переносима, но то, что она делает, не обязательно очень полезно, поскольку она копирует не то, что любой разумный пользователь считает «файлом», а только содержимое файла.
3. Исходный код
cp --preserve
должен дать представление о том, что еще вы, возможно, захотите скопировать, и как это сделать в Linux.4. @SteveJessop да, вот почему я выделил курсивом «больше» и предложил использовать функции копирования из Python или bash, а не копировать содержимое файла с помощью функций C.
Ответ №2:
Вот как я бы это сделал. Это довольно просто и оставляет сложную часть фактического копирования cp
инструменту, который успешно выполняет эту задачу в течение нескольких лет.
#include <assert.h>
#include <string.h>
#include <sys/wait.h>
#include <unistd.h>
int
runvp(int *ret_status, const char *command, const char * const *argv)
{
pid_t pid;
int status;
char * const *execv_argv;
pid = fork();
if (pid == (pid_t) -1)
return -1;
if (pid == 0) {
/*
* Circumvent the C type conversion rules;
* see ISO C99: 6.5.16.1#6 for details.
*/
assert(sizeof(execv_argv) == sizeof(argv));
memcpy(amp;execv_argv, amp;argv, sizeof(execv_argv));
(void) execvp(command, execv_argv);
return -1;
}
if (waitpid(pid, amp;status, 0) == -1)
return -1;
*ret_status = status;
return 0;
}
Это оболочка fork
, execvp
которую я написал несколько лет назад. Его можно использовать следующим образом:
#include <stdio.h>
#include <stdlib.h>
int main(int argc, char **argv) {
int exitcode;
const char *cmdline[] = {
"cp",
"--",
argv[1],
argv[2],
NULL
};
if (runvp(amp;exitcode, cmdline[0], cmdline) == -1) {
perror("runvp");
return EXIT_FAILURE;
}
return EXIT_SUCCESS;
}
Комментарии:
1. Плохая идея. Вы теряете всякую возможность определить, что пошло не так, если
cp
обнаружите ошибку, плюс в процессе он будет передавать что-то в stderr, плюс он подберет любой «cp», который окажется на ПУТИ (т. Е. Потенциальная дыра в безопасности), плюс это длиннее и сложнее, чем просто написать свою собственную копиюфункция.
Ответ №3:
rename() должен работать. Вы проверили ошибку, которую он возвращает? rename() возвращает 0, если это удалось в соответствии с документацией:
http://www.cplusplus.com/reference/clibrary/cstdio/rename/
Вы можете использовать perror() для вывода строки ошибки в стандартную ошибку (stderr, обычно экран):