Ejemplo n.º 1
0
/* if *file represents a directory, moves all its contents into *to, else renames
 * file itself to *to. */
int BLI_move(const char *file, const char *to)
{
	int ret = recursive_operation(file, to, move_callback_pre, move_single_file, NULL);

	if (ret && ret != -1) {
		return recursive_operation(file, NULL, NULL, delete_single_file, delete_callback_post);
	}

	return ret;
}
Ejemplo n.º 2
0
int BLI_copy(const char *file, const char *to)
{
	char *actual_to = check_destination(file, to);
	int ret;

	ret = recursive_operation(file, actual_to, copy_callback_pre, copy_single_file, NULL);

	if (actual_to != to)
		MEM_freeN(actual_to);

	return ret;
}
Ejemplo n.º 3
0
/**
 * Deletes the specified file or directory (depending on dir), optionally
 * doing recursive delete of directory contents.
 */
int BLI_delete(const char *file, bool dir, bool recursive)
{
	if (recursive) {
		return recursive_operation(file, NULL, NULL, delete_single_file, delete_callback_post);
	}
	else if (dir) {
		return rmdir(file);
	}
	else {
		return remove(file);
	}
}
Ejemplo n.º 4
0
/**
 * Deletes the specified file or directory (depending on dir), optionally
 * doing recursive delete of directory contents.
 */
int BLI_delete(const char *file, bool dir, bool recursive)
{
	if (strchr(file, '"')) {
		printf("Error: not deleted file %s because of quote!\n", file);
	}
	else {
		if (recursive) {
			return recursive_operation(file, NULL, NULL, delete_single_file, delete_callback_post);
		}
		else if (dir) {
			return rmdir(file);
		}
		else {
			return remove(file); //BLI_snprintf(str, sizeof(str), "/bin/rm -f \"%s\"", file);
		}
	}
	return -1;
}
Ejemplo n.º 5
0
/**
 * Scans \a startfrom, generating a corresponding destination name for each item found by
 * prefixing it with startto, recursively scanning subdirectories, and invoking the specified
 * callbacks for files and subdirectories found as appropriate.
 *
 * \param startfrom  Top-level source path.
 * \param startto  Top-level destination path.
 * \param callback_dir_pre  Optional, to be invoked before entering a subdirectory, can return
 *                          RecursiveOp_Callback_StopRecurs to skip the subdirectory.
 * \param callback_file  Optional, to be invoked on each file found.
 * \param callback_dir_post  optional, to be invoked after leaving a subdirectory.
 * \return
 */
static int recursive_operation(const char *startfrom, const char *startto,
                               RecursiveOp_Callback callback_dir_pre,
                               RecursiveOp_Callback callback_file, RecursiveOp_Callback callback_dir_post)
{
	struct stat st;
	char *from = NULL, *to = NULL;
	char *from_path = NULL, *to_path = NULL;
	struct dirent **dirlist = NULL;
	size_t from_alloc_len = -1, to_alloc_len = -1;
	int i, n, ret = 0;

	do {  /* once */
		/* ensure there's no trailing slash in file path */
		from = strip_last_slash(startfrom);
		if (startto)
			to = strip_last_slash(startto);

		ret = lstat(from, &st);
		if (ret < 0)
			/* source wasn't found, nothing to operate with */
			break;

		if (!S_ISDIR(st.st_mode)) {
			/* source isn't a directory, can't do recursive walking for it,
			 * so just call file callback and leave */
			if (callback_file != NULL) {
				ret = callback_file(from, to);
				if (ret != RecursiveOp_Callback_OK)
					ret = -1;
			}
			break;
		}

		n = scandir(startfrom, &dirlist, NULL, alphasort);
		if (n < 0) {
			/* error opening directory for listing */
			perror("scandir");
			ret = -1;
			break;
		}

		if (callback_dir_pre != NULL) {
			ret = callback_dir_pre(from, to);
			if (ret != RecursiveOp_Callback_OK) {
				if (ret == RecursiveOp_Callback_StopRecurs)
					/* callback requested not to perform recursive walking, not an error */
					ret = 0;
				else
					ret = -1;
				break;
			}
		}

		for (i = 0; i < n; i++) {
			const struct dirent * const dirent = dirlist[i];

			if (!strcmp(dirent->d_name, ".") || !strcmp(dirent->d_name, ".."))
				continue;

			join_dirfile_alloc(&from_path, &from_alloc_len, from, dirent->d_name);
			if (to)
				join_dirfile_alloc(&to_path, &to_alloc_len, to, dirent->d_name);

			if (dirent->d_type == DT_DIR) {
				/* recursively dig into a subfolder */
				ret = recursive_operation(from_path, to_path, callback_dir_pre, callback_file, callback_dir_post);
			}
			else if (callback_file != NULL) {
				ret = callback_file(from_path, to_path);
				if (ret != RecursiveOp_Callback_OK)
					ret = -1;
			}

			if (ret != 0)
				break;
		}
		if (ret != 0)
			break;

		if (callback_dir_post != NULL) {
			ret = callback_dir_post(from, to);
			if (ret != RecursiveOp_Callback_OK)
				ret = -1;
		}
	}
	while (false);

	if (dirlist != NULL) {
		for (i = 0; i < n; i++) {
			free(dirlist[i]);
		}
		free(dirlist);
	}
	if (from_path != NULL)
		MEM_freeN(from_path);
	if (to_path != NULL)
		MEM_freeN(to_path);
	if (from != NULL)
		MEM_freeN(from);
	if (to != NULL)
		MEM_freeN(to);

	return ret;
}