⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 unpack.c

📁 一套客户/服务器模式的备份系统代码,跨平台,支持linux,AIX, IRIX, FreeBSD, Digital Unix (OSF1), Solaris and HP-UX.
💻 C
📖 第 1 页 / 共 5 页
字号:
/****************** Start of $RCSfile: unpack.c,v $  ****************** $Source: /home/alb/afbackup/afbackup-3.3.8.1/RCS/unpack.c,v $* $Id: unpack.c,v 1.5 2005/01/24 18:58:10 alb Exp alb $* $Date: 2005/01/24 18:58:10 $* $Author: alb $********* description *********************************************************************************************************************/#include <conf.h>#include <version.h>  static char * fileversion = "$RCSfile: unpack.c,v $ $Source: /home/alb/afbackup/afbackup-3.3.8.1/RCS/unpack.c,v $ $Id: unpack.c,v 1.5 2005/01/24 18:58:10 alb Exp alb $ " PACKAGE " " VERSION_STRING;#include <stdio.h>#include <string.h>#include <errno.h>#include <sys/types.h>#ifdef	HAVE_SYS_PARAM_H#include <sys/param.h>#endif#include <dirent.h>#include <fcntl.h>#ifdef	HAVE_SYS_TIME_H#include <sys/time.h>#endif#ifdef	HAVE_SYS_WAIT_H#include <sys/wait.h>#endif#include <signal.h>#include <utime.h>#include <unistd.h>#include <genutils.h>#include <fileutil.h>#include <packer.h>#if defined(USE_SOLARIS2_ACLS) || defined(USE_HPUX10_ACLS) || defined(USE_POSIX_ACLS)#include <sys/acl.h>#endif#ifdef	USE_ZLIB#include <zutils.h>#define	write_file(fd, cp, n, z, e, f)	write_file_unzip(z, cp, n, e, f)#else	/* defined(USE_ZLIB) */#define	write_file(fd, cp, n, z, e, f)	(*f)(fd, cp, n)#endif	/* defined(USE_ZLIB) */#define	CLEANUPR(x)	{ r = x; goto cleanup; }typedef	struct __solaris2_acl__ {  int	acltype;  int	nacls;  void	*acls;} Solaris2ACL;typedef	Solaris2ACL	HPUX10ACL;	/* quite the same for us */typedef struct __posix_acl__ {  int	acltype;  int	acl_types;  void	*acl_arr[3];} POSIXACL;typedef struct __unknown_acl__ {  int	acltype;} UnknownACL;#define	ZFREE_ACL_STRUCT(acls, params)	{ if(acls){	\		free_acl_struct(acls, params); acls = NULL; }}static voidfree_acl_struct(void * acls, AarParams * params){  if(!acls)    return;  switch(((UnknownACL *) acls)->acltype){    case SOLARIS2_ACL:	ZFREE(((Solaris2ACL *) acls)->acls);	break;    case HPUX10_ACL:	ZFREE(((HPUX10ACL *) acls)->acls);	break;    case POSIX_ACL:#ifdef	USE_POSIX_ACLS      {	Int32	i, acl_types;	acl_t	acl;	acl_types = ((POSIXACL *) acls)->acl_types;	for(i = 0; i < 3; i++){	  if(acl_types & (1 << i)){	    if( (acl = ((POSIXACL *) acls)->acl_arr[i]) ){	      acl_free(acl);	      ((POSIXACL *) acls)->acl_arr[i] = (acl_t) 0;	    }	  }	}      }#endif	break;    default:	fprintf(params->errfp,		"Warning: Unkknown ACL type %d, possible memory"		" leak - should never happen.\n",		((UnknownACL *) acls)->acltype);	return;  }  free(acls);}static Int32get_int(AarParams * params, Int32 * rptr){  Int32		i, s;  UChar		c, n;  Int32		r;  n = 0;  r = 0;  s = 1;  forever{    i = params->inputfunc(&c, 1, params);    if(i == 0)	return(-1);    if(c == ';')	break;    if(c == '-'){	if(n || s == -1)	  return(0);	s = -1;    }    else if(isspace(c)){	continue;    }    else if(c <= '9' && c >= '0'){	r = (r << 3) + (r << 1) + (c - '0');	n = 1;    }    else	return(0);  }  if(!n)    return(0);  *rptr = r * s;  return(1);}    static Int32get_uns(AarParams * params, Uns32 * rptr){  Int32		i;  UChar		c, n;  Uns32		r;  n = 0;  r = 0;  forever{    i = params->inputfunc(&c, 1, params);    if(i == 0)	return(-1);    if(c == ';')	break;    if(isspace(c)){	continue;    }    else if(c <= '9' && c >= '0'){	r = (r << 3) + (r << 1) + (c - '0');	n = 1;    }    else	return(0);  }  if(!n)    return(0);  *rptr = r;  return(1);}static Int32get_time_t(AarParams * params, time_t * rptr){  Int32		i, s;  UChar		c, n;  time_t	r;  n = 0;  r = (time_t) 0;  s = 1;		/* time_t can be fucking negative */  forever{    i = params->inputfunc(&c, 1, params);    if(i == 0)	return(-1);    if(c == ';')	break;    if(c == '-'){	if(n || s == -1)	  return(0);	s = -1;    }    else if(isspace(c)){	continue;    }    else if(c <= '9' && c >= '0'){	r = (r << 3) + (r << 1) + (c - '0');	n = 1;    }    else	return(0);  }  if(!n)    return(0);  *rptr = r * s;  return(1);}    static Int32get_size_t(AarParams * params, size_t * rptr){  Int32		i;  UChar		c, n;  size_t	r;  n = 0;  r = (size_t) 0;  forever{    i = params->inputfunc(&c, 1, params);    if(i == 0)	return(-1);    if(c == ';')	break;    if(isspace(c)){	continue;    }    else if(c <= '9' && c >= '0'){	r = (r << 3) + (r << 1) + (c - '0');	n = 1;    }    else	return(0);  }  if(!n)    return(0);  *rptr = r;  return(1);}    static Int32get_off_t(AarParams * params, off_t * rptr){  Int32		i;  UChar		c, n;  off_t		r;  n = 0;  r = (off_t) 0;  forever{    i = params->inputfunc(&c, 1, params);    if(i == 0)	return(-1);    if(c == ';')	break;    if(isspace(c)){	continue;    }    else if(c <= '9' && c >= '0'){	r = (r << 3) + (r << 1) + (c - '0');	n = 1;    }    else	return(0);  }  if(!n)    return(0);  *rptr = r;  return(1);}    static Int32name_in_list(  UChar		*name,  UChar		**list,  Int32		len,  UChar		subdir,  UChar		*found){  UChar		**listptr;  if(!list)    return(1);  if(len < 0)    for(len = 0, listptr = list; *listptr; listptr++, len++);  if(!subdir){    listptr = (UChar **)		b_search(&name, list, len, sizeof(UChar *), cmp_UCharPTR);    if(listptr){	found[listptr - list] = 1;	return(1);    }    return(0);  }	  if(subdir)    for(; *list; list++, found++){      len = strlen(*list);      if(!strcmp(*list, name) ||		(!strncmp(*list, name, len) && (name[len] == FN_DIRSEPCHR				|| name[len - 1] == FN_DIRSEPCHR))){	*found = 1;	return(1);      }    }  return(0);}static Int32formaterr(Int32 * type, AarParams * params, Flag started){  Int32	i;  Int32	li;  if(!(!started && params->skip_garbage)){    fprintf(params->errfp,	T_("Error: format error in input, trying to skip to the next file ...\n"));    params->vars.errnum |= EUNPACKFORMAT;  }  forever{    if(params->pre_verbosefunc)	(*params->pre_verbosefunc)(NULL, params);    i = get_int(params, &li);    if(i < 0)	return(-1);	/* -1 */    if(i == 1){	*type = (Int32) li;	return(1);    }  }}#define	read_int(val, typ)	{ rvr = get_int(params, &li); \				  if(rvr < 1){ \				    i = formaterr(&type, params, started); \				    have_an_error = YES; \				    goto tryagain; \				  } \				  val = (typ) li; }#define	read_uns(val, typ)	{ rvr = get_uns(params, &lu); \				  if(rvr < 1){ \				    i = formaterr(&type, params, started); \				    have_an_error = YES; \				    goto tryagain; \				  } \				  val = (typ) lu; }#define	read_time_t(val, typ)	{ rvr = get_time_t(params, &ltt); \				  if(rvr < 1){ \				    i = formaterr(&type, params, started); \				    have_an_error = YES; \				    goto tryagain; \				  } \				  val = (typ) ltt; }#define	read_size_t(val, typ)	{ rvr = get_size_t(params, &stt); \				  if(rvr < 1){ \				    i = formaterr(&type, params, started); \				    have_an_error = YES; \				    goto tryagain; \				  } \				  val = (typ) stt; }#define	read_off_t(val, typ)	{ rvr = get_off_t(params, &ott); \				  if(rvr < 1){ \				    i = formaterr(&type, params, started); \				    have_an_error = YES; \				    goto tryagain; \				  } \				  val = (typ) ott; }#define	POSZ(x)			{ if(x < 0) x = 0; }#define	DP			"--> "	/* the DIFFERENCES_PREFIX */static Flaginvalid_time_or_uid(time_t mtime, int uid, AarParams * params){  return((params->uid && params->uid != uid)		|| (params->time_older && params->time_older <= mtime)		|| (params->time_newer && params->time_newer > mtime));}static Flagnot_allowed(UChar * name, AarParams * params){  UChar		lname[MAXPATHLEN * 2 + 2], *cptr;  uid_t		uid;  Flag		r;		/* uninitialized ok */  struct stat	statb;  if(!(uid = params->uid))    CLEANUPR(NO);  if(!name[0])    CLEANUPR(YES);  strcpy(lname, name);  cleanpath(lname);  forever{    if(!stat(lname, &statb))	/* fs-entry exists, can read it */	CLEANUPR(statb.st_uid != uid ? YES : NO);    cptr = FN_LASTDIRDELIM(lname);	/* get last / */    if(cptr)	*cptr = '\0';    if(!lname[0])	CLEANUPR(YES);		/* was absolute path, at root now */    if(!cptr){			/* name remaining in current dir */	if(stat(FN_CURDIR, &statb))	  CLEANUPR(YES);	CLEANUPR(statb.st_uid != uid ? YES : NO);    }  } cleanup:  if(r){    fprintf(params->errfp,		T_("Error: No write permission for `%s'.\n"), name);    params->vars.errnum |= EUNPACKACCESS;  }  return(r);}Int32pack_contents(AarParams * params){  UChar		buf[BUFFERSIZ], buf2[BUFFERSIZ];  UChar		verbosestr[MAXPATHLEN * 2 + 100], c, *cptr;  Flag		have_an_error, started, var_compr, fmterr;  Flag		compressed, builtin_uncompress;  Uns8		verbose;  Int32		type, i, j, k, n, uid, gid, ifd, rvr;  Uns32		mode, lu;  time_t	mtime, ltt;  size_t	len, stt;  off_t		filelen, ott;  FILE		*errfp;  Int32		li;  int		pid, pst, pp[2], ucfd;  dev_t		rdev;  void		*to_be_freed = NULL;  void		(*verbosefunc)(UChar *, struct aar_params *);  Int32		(*writefunc)(int, UChar *, Int32);  Flag		cks, biu_error;  Uns32		crc32sum;	/* uninitialized OK */  errfp = params->errfp;  verbose = params->verbose;  verbosefunc = params->verbosefunc;  if(!verbosefunc)    verbosefunc = pack_default_verbose;  ifd = params->infd;  writefunc = params->writefunc;  started = have_an_error = NO;  forever{    pid = -1;    if(params->pre_verbosefunc)	(*params->pre_verbosefunc)(NULL, params);    i = get_int(params, &li);    type = (Int32) li;   tryagain:    if(i < 1){	if(i < 0)	  return(EOF);	i = formaterr(&type, params, started);	have_an_error = YES;	goto tryagain;    }    type = (ABS(type) & PACK_TYPEMASK) * SIGN(type);     cks = NO;    switch(type){      case ENDOFARCHIVE:	if(have_an_error){	  i = formaterr(&type, params, started);	  goto tryagain;	}	return(0);      case INFORMATION:	read_size_t(len, size_t);	if(len + 1 > BUFFERSIZ)	  cptr = to_be_freed = NEWP(UChar, len + 1);	else	  cptr = buf;	i = params->inputfunc(cptr, len, params);	if(i < len){	  ZFREE(to_be_freed);	  goto eoferr;	}	i = params->inputfunc(&c, 1, params);	if(c != '.' || i < 1){	  ZFREE(to_be_freed);	  i = formaterr(&type, params, started);	  have_an_error = YES;	  goto tryagain;	}	cptr[len] = '\0';	verbosefunc(cptr, params);	ZFREE(to_be_freed);	started = YES;	have_an_error = NO;	break;	      case DIRECTORY:	read_uns(mode, Uns32);	read_time_t(mtime, time_t);	read_int(uid, Int32);	read_int(gid, Int32);	read_size_t(len, size_t);	i = params->inputfunc(buf, len, params);	if(i < len)	  goto eoferr;	buf[len] = '\0';	i = params->inputfunc(&c, 1, params);	if(c != '.' || i < 1){	  i = formaterr(&type, params, started);	  have_an_error = YES;	  goto tryagain;	}	mk_esc_seq(buf, ESCAPE_CHARACTER, verbosestr);	if(verbose)	  strcat(verbosestr, "/");	strcat(verbosestr, "\n");	params->vars.uid = uid;	params->vars.mtime = mtime;	verbosefunc(verbosestr, params);	started = YES;	have_an_error = NO;	break;      case FIFO:      case SOCKET:	read_uns(mode, Uns32);	read_time_t(mtime, time_t);	read_int(uid, Int32);	read_int(gid, Int32);	read_size_t(len, size_t);	i = params->inputfunc(buf, len, params);	if(i < 1)	  goto eoferr;	buf[len] = '\0';	mk_esc_seq(buf, ESCAPE_CHARACTER, verbosestr);	if(verbose)	  strcat(verbosestr, (type == FIFO ? "|" : "["));	strcat(verbosestr, "\n");	params->vars.uid = uid;	params->vars.mtime = mtime;	verbosefunc(verbosestr, params);	i = params->inputfunc(&c, 1, params);	if(c != '.' || i < 1){	  i = formaterr(&type, params, started);	  have_an_error = YES;	  goto tryagain;	}	started = YES;	have_an_error = NO;	break;      case BLOCKDEVICE:      case CHARDEVICE:	read_uns(mode, Uns32);	read_time_t(mtime, time_t);	read_int(uid, Int32);	read_int(gid, Int32);	read_uns(rdev, dev_t);	read_size_t(len, size_t);	i = params->inputfunc(buf, len, params);	if(i < 1)	  goto eoferr;	buf[len] = '\0';	mk_esc_seq(buf, ESCAPE_CHARACTER, verbosestr);	if(verbose)	  strcat(verbosestr, (type == BLOCKDEVICE ? "#" : "*"));	strcat(verbosestr, "\n");	params->vars.uid = uid;	params->vars.mtime = mtime;	verbosefunc(verbosestr, params);	i = params->inputfunc(&c, 1, params);	if(c != '.' || i < 1){	  i = formaterr(&type, params, started);	  have_an_error = YES;	  goto tryagain;	}	started = YES;	have_an_error = NO;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -