现在的位置: 首页 > 综合 > 正文

目录和文件拷贝学习笔记

2013年04月02日 ⁄ 综合 ⁄ 共 3549字 ⁄ 字号 评论关闭
#include <dirent.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#define	BUFFER_SIZE	1024	/* 每次读写缓存大小,影响运行效率 */
#define _LARRGEFILE_SOURCE
#define _LARRGEFILE64_SOURCE
#define _FILE_OFFSET_BITS 64
#define	OFFSET	10240	/* 复制的数据大小 */     
int cp_dir(const char *src,const char*dst);
int cp_file(char * src1,char *dst2,mode_t mode);
int main(int argc,char *argv[])
{
	struct stat stat_src;
	if(argc<3)
	{
		fprintf(stderr,"usage %s src_dir dsr_src\n",argv[0]);
		exit(EXIT_FAILURE);
	}
	if(stat(argv[1],&stat_src)!=0)//获得源文件属性 
	{
		fprintf(stderr,"%s(%d):stat error(%s)!\n",
		(char *)__FILE__,__LINE__,(char *)strerror(errno));
		exit(EXIT_FAILURE);
	}
	umask(0000);
	if(S_ISREG(stat_src.st_mode))//如果为普通文件 
	{
		struct stat stat_dst;
		if(stat(argv[2],&stat_dst)==-1)//读取目标文件属性 
		{
			
		
			if(errno!=ENOENT)
			{
				fprintf(stderr,"%s(%d):stat error(%s)!\n",
				(char *)__FILE__,__LINE__,(char *)strerror(errno));
				exit(EXIT_FAILURE);
			}
			else
			{
				cp_file(argv[1],argv[2],stat_src.st_mode);//复制文件 
			}
		}
	
		else
		{
			if(S_ISDIR(stat_dst.st_mode))//如果目标是目录 
			{
				char *ptr=(char*)malloc(strlen(argv[2])+1+strlen(argv[1])+1);//分配内存 
				sprintf(ptr,"%s/%s\0",argv[2],argv[1]);
				cp_file(argv[1],ptr,stat_src.st_mode);	
			}
			else
			{
				printf("file %s exit,do you want over want overwrite it[y/n]",argv[2]);	
				char ch;
				while(!scanf("%c",&ch))
				{
					getchar();	
				}
				if(ch=='Y'||ch=='y')//y就拷贝文件 
				{
					unlink(argv[2]);
					cp_file(argv[1],argv[2],stat_src.st_mode);	
					
				}
				else
				return 1;
			}	
		}
	}
	else if(S_ISDIR(stat_src.st_mode))//如果源文件是目录 
	{
		struct stat stat_dst;
		if(stat(argv[2],&stat_dst)==-1)//读取目标文件属性 
		{
			if(errno!=ENOENT)
			{
						fprintf(stderr,"%s(%d):stat error(%s)!\n",
					(char *)__FILE__,__LINE__,(char *)strerror(errno));
					exit(EXIT_FAILURE);
			}
			else
			{
				errno=0;
				if(-1==mkdir(argv[2],stat_src.st_mode))//创建目标目录 
				{
					perror("mkdir1");
					exit(EXIT_FAILURE);
				}
				cp_dir(argv[1],argv[2]);//复制目录 
				
			}
		}
		else if(S_ISREG(stat_dst.st_mode))
		{
			fprintf(stderr,"cant copy a dir to a file \n");
			exit(EXIT_FAILURE);
		}
		else
		{
			
			char *ptr=(char *)malloc(strlen(argv[1])+1+strlen(argv[2])+1);
			sprintf(ptr,"%s /%s\0",argv[2],argv[1]);
			if(-1==mkdir(ptr,stat_src.st_mode))
			{
				perror("mkdir2");
				exit(EXIT_FAILURE);
			}
			cp_dir(argv[1],ptr);
		
			free(ptr);
		}
		
	}
}
int cp_dir(const char *src,const char*dst)
{
		DIR	 *dirp=NULL;
		
		if(NULL==(dirp=opendir(src)))
		{
			perror("opendir");
			exit(EXIT_FAILURE);	
		}
		struct dirent *entp=NULL;
		while(NULL !=(entp=readdir(dirp)))//读取目录 内容 
		{
			if(strcmp(entp->d_name,"..")==0||strcmp(entp->d_name,".")==0) //如果当前 目录和上级目录,忽略 
			{
				continue;
			}
			char * name_src=(char *)malloc(strlen(src)+1+strlen(entp->d_name)+1);
			sprintf(name_src,"%s/%s\0",src,entp->d_name);
			char *name_dst=	(char *)malloc(strlen(dst)+1+strlen(entp->d_name)+1);
			sprintf(name_dst,"%s/%s\0",dst,entp->d_name);
			struct	 stat stat_src;
			if(stat(name_src,&stat_src)==-1)//读取源文件属性 
			{
				fprintf(stderr,"%s(%d):stat error(%s)!\n",__FILE__,__LINE__,strerror(errno));
				exit(EXIT_FAILURE);
			}
			if(S_ISREG(stat_src.st_mode))//普通文件 
			{
				cp_file(name_src,name_dst,stat_src.st_mode);
				free(name_src);
				free(name_dst);
			}
			else if(S_ISDIR(stat_src.st_mode))//是目录 
			{
				if(-1==mkdir(name_dst,stat_src.st_mode))
				{
					perror("mkdir3");
					exit(EXIT_FAILURE);
				}
				cp_dir(name_src,name_dst);
				free(name_dst);
				free(name_src);	
			}
		}
		
}

int cp_file(char * src1,char *dst2,mode_t  mode)
{
	int src_file, dest_file;
	unsigned char buff[BUFFER_SIZE];
	int real_read_len;

	/* 以只读方式打开源文件 */
	src_file = open(src1, O_RDONLY);

	/* 以只写方式打开目标文件,若此文件不存在则创建该文件,访问权限值为644 */
	dest_file = open(dst2, O_WRONLY | O_CREAT, 
		S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
	if(src_file < 0 || dest_file < 0)
	{
		printf("Open file error\n");
		exit(1);
	}



	/* 读取源文件的数据并写到目标文件中,每次读写1KB */
	do		
	{
		real_read_len = read(src_file, buff,BUFFER_SIZE);
		
		write(dest_file, buff, real_read_len);
	}while(real_read_len==BUFFER_SIZE);

	close(dest_file);
	close(src_file);
	return 0;
}

【上篇】
【下篇】

抱歉!评论已关闭.