Exemplo n.º 1
0
static void print_value(int output, int num, const char *devname,
			const char *value, const char *name, size_t valsz)
{
	if (output & OUTPUT_VALUE_ONLY) {
		fputs(value, stdout);
		fputc('\n', stdout);

	} else if (output & OUTPUT_UDEV_LIST) {
		print_udev_format(name, value, valsz);

	} else if (output & OUTPUT_EXPORT_LIST) {
		fputs(name, stdout);
		fputs("=", stdout);
		safe_print(value, valsz);
		fputs("\n", stdout);

	} else {
		if (num == 1 && devname)
			printf("%s: ", devname);
		fputs(name, stdout);
		fputs("=\"", stdout);
		safe_print(value, valsz);
		fputs("\" ", stdout);
	}
}
Exemplo n.º 2
0
/* Print out ID3v1 info. */
void print_v1(mpg123_id3v1 *v1)
{
	safe_print("Title",   v1->title,   sizeof(v1->title));
	safe_print("Artist",  v1->artist,  sizeof(v1->artist));
	safe_print("Album",   v1->album,   sizeof(v1->album));
	safe_print("Year",    v1->year,    sizeof(v1->year));
	safe_print("Comment", v1->comment, sizeof(v1->comment));
	printf("Genre: %i", v1->genre);
}
Exemplo n.º 3
0
static int
safe_printpath(const FTSENT *p) {
	int chcnt;

	if (f_fullpath) {
		chcnt = safe_print(p->fts_path);
		chcnt += safe_print("/");
	} else
		chcnt = 0;
	return chcnt + safe_print(p->fts_name);
}
Exemplo n.º 4
0
void StatisticsBase::safeFlushInformation(int fd) const {
#ifdef CVC4_STATISTICS_ON
  for (StatSet::iterator i = d_stats.begin(); i != d_stats.end(); ++i) {
    Stat* s = *i;
    if (d_prefix.size() != 0) {
      safe_print(fd, d_prefix);
      safe_print(fd, s_regDelim);
    }
    s->safeFlushStat(fd);
    safe_print(fd, "\n");
  }
#endif /* CVC4_STATISTICS_ON */
}
static void NORETURN spawn_child_process( int from_parent )
{
	/* We need to re-exec ourself, to get a clean process.  Close all
	 * FDs except for 0-2 and to_child, and then assign to_child to 3. */
	for( int fd = 3; fd < 1024; ++fd )
		if( fd != from_parent ) close(fd);

	if( from_parent != 3 )
	{
		dup2( from_parent, 3 );
		close( from_parent );
	}

	char path[1024];
	char magic[32];
	GetExecutableName( path, sizeof(path) );
	strncpy( magic, CHILD_MAGIC_PARAMETER, sizeof(magic) );

	/* Use execve; it's the lowest-level of the exec calls.  The others may allocate. */
	char *argv[3] = { path, magic, NULL };
	char *envp[1] = { NULL };
	execve( path, argv, envp );

	/* If we got here, the exec failed.  We can't call strerror. */
	// safe_print(fileno(stderr), "Crash handler execl(", path, ") failed: ", strerror(errno), "\n", NULL);
	safe_print( fileno(stderr), "Crash handler execl(", path, ") failed: ", itoa( errno ), "\n", NULL );
	_exit(1);
}
Exemplo n.º 6
0
/*
 * print [inode] [size] name
 * return # of characters printed, no trailing characters.
 */
static int
printaname(FTSENT *p, int inodefield, int sizefield)
{
	struct stat *sp;
	int chcnt;
	char szbuf[5];

	sp = p->fts_statp;
	chcnt = 0;
	if (f_inode)
		chcnt += printf("%*lu ", inodefield, (unsigned long)sp->st_ino);
	if (f_size) {
		if (f_humanize) {
			if ((humanize_number(szbuf, sizeof(szbuf), sp->st_size,
			    "", HN_AUTOSCALE,
			    (HN_DECIMAL | HN_B | HN_NOSPACE))) == -1)
				err(1, "humanize_number");
			chcnt += printf("%*s ", sizefield, szbuf);
		} else {
			chcnt += printf("%*llu ", sizefield,
			    (long long)howmany(sp->st_blocks, blocksize));
		}
	}
	if (f_octal || f_octal_escape)
		chcnt += safe_print(p->fts_name);
	else if (f_nonprint)
		chcnt += printescaped(p->fts_name);
	else
		chcnt += printf("%s", p->fts_name);
	if (f_type || (f_typedir && S_ISDIR(sp->st_mode)))
		chcnt += printtype(sp->st_mode);
	return (chcnt);
}
static bool parent_write( int to_child, const void *p, size_t size )
{
	int ret = retried_write( to_child, p, size );
	if( ret == -1 )
	{
		safe_print( fileno(stderr), "Unexpected write() result (", strerror(errno), ")\n", NULL );
		return false;
	}

	if( size_t(ret) != size )
	{
		safe_print( fileno(stderr), "Unexpected write() result (", itoa(ret), ")\n", NULL );
		return false;
	}

	return true;
}
Exemplo n.º 8
0
static ssize_t irc_write(int fd, const char *text) {
  char msg[BUFLEN];

  snprintf(msg, BUFLEN, "%s\r\n", text);

  if(verbose > IRC_MSG) safe_print('>', text);

  return write(fd, msg, strlen(msg));
}
Exemplo n.º 9
0
int main(int argc, char* argv[]) {

	char* prefix;
	char* buf;
	int  len;
	int  i;
	int  result;

	if (argc < 3) {
		help();
		return EXIT_FAILURE;
	}
	
	len = strlen(argv[1]);
	if (len == 0) {
		fprintf(stderr, "empty string\n");
		return EXIT_FAILURE;
	}
	
	prefix = malloc(len+1);
	if (prefix == NULL) {
		fprintf(stderr, "can't allocate %d byte(s)\n", len+1);
		return EXIT_FAILURE;
	}
	
	/* any escapes? */
	len = parse_string(argv[1], prefix);
#ifdef DEBUG
	printf("len = %d, ", len);
	safe_print(prefix, len);
	putchar('\n');
#endif

	buf = malloc(len);
	if (buf == NULL) {
		free(prefix);
		fprintf(stderr, "can't allocate %d byte(s)\n", len);
		return EXIT_FAILURE;
	}

	errno = 0;
	if (argc == 3) {	// just one file
		result = match(argv[2], prefix, len, buf) ?
				EXIT_SUCCESS : EXIT_FAILURE;
	}
	else // more files
	for (i=2; i < argc; i++) {
		result = EXIT_SUCCESS;
		if (match(argv[i], prefix, len, buf))
			puts(argv[i]);
	}

	free(buf);
	free(prefix);

	return result;
}
Exemplo n.º 10
0
void cvc4terminate() {
  set_terminate(default_terminator);
#ifdef CVC4_DEBUG
  LastExceptionBuffer* current = LastExceptionBuffer::getCurrent();
  LastExceptionBuffer::setCurrent(NULL);
  delete current;

  safe_print(STDERR_FILENO,
             "\n"
             "CVC4 was terminated by the C++ runtime.\n"
             "Perhaps an exception was thrown during stack unwinding.  "
             "(Don't do that.)\n");
  print_statistics();
  default_terminator();
#else /* CVC4_DEBUG */
  safe_print(STDERR_FILENO,
             "CVC4 was terminated by the C++ runtime.\n"
             "Perhaps an exception was thrown during stack unwinding.\n");
  print_statistics();
  default_terminator();
#endif /* CVC4_DEBUG */
}
Exemplo n.º 11
0
static void print_tags(blkid_dev dev, char *show[], int numtag, int output)
{
	blkid_tag_iterate	iter;
	const char		*type, *value;
	int 			i, first = 1;

	if (!dev)
		return;

	if (output & OUTPUT_PRETTY_LIST) {
		pretty_print_dev(dev);
		return;
	}

	if (output & OUTPUT_DEVICE_ONLY) {
		printf("%s\n", blkid_dev_devname(dev));
		return;
	}

	iter = blkid_tag_iterate_begin(dev);
	while (blkid_tag_next(iter, &type, &value) == 0) {
		if (numtag && show) {
			for (i=0; i < numtag; i++)
				if (!strcmp(type, show[i]))
					break;
			if (i >= numtag)
				continue;
		}
		if (output & OUTPUT_VALUE_ONLY) {
			fputs(value, stdout);
			fputc('\n', stdout);
		} else {
			if (first) {
				printf("%s: ", blkid_dev_devname(dev));
				first = 0;
			}
			fputs(type, stdout);
			fputs("=\"", stdout);
			safe_print(value, -1);
			fputs("\" ", stdout);
		}
	}
	blkid_tag_iterate_end(iter);

	if (!first && !(output & OUTPUT_VALUE_ONLY))
		printf("\n");
}
Exemplo n.º 12
0
/*
 * This function prints a pathname, using the ext2fs_get_pathname
 * function
 */
static void print_pathname(ext2_filsys fs, ext2_ino_t dir, ext2_ino_t ino)
{
	errcode_t	retval;
	char		*path;

	if (!dir && (ino < num_special_inodes)) {
		fputs(_(special_inode_name[ino]), stdout);
		return;
	}
	
	retval = ext2fs_get_pathname(fs, dir, ino, &path);
	if (retval)
		fputs("???", stdout);
	else {
		safe_print(path, -1);
		ext2fs_free_mem(&path);
	}
}
Exemplo n.º 13
0
/*
 * This function prints a pathname, using the ext2fs_get_pathname
 * function
 */
static void print_pathname(FILE *f, ext2_filsys fs, ext2_ino_t dir,
			   ext2_ino_t ino)
{
	errcode_t	retval = 0;
	char		*path;

	if (!dir && (ino < num_special_inodes)) {
		fputs(_(special_inode_name[ino]), f);
		return;
	}

	if (fs)
		retval = ext2fs_get_pathname(fs, dir, ino, &path);
	if (!fs || retval)
		fputs("???", f);
	else {
		safe_print(f, path, -1);
		ext2fs_free_mem(&path);
	}
}
Exemplo n.º 14
0
/*
 * This function expands '%dX' expressions
 */
static _INLINE_ void expand_dirent_expression(ext2_filsys fs, char ch,
					      struct problem_context *ctx)
{
	struct ext2_dir_entry	*dirent;
	unsigned int rec_len;
	int	len;

	if (!ctx || !ctx->dirent)
		goto no_dirent;

	dirent = ctx->dirent;

	switch (ch) {
	case 'i':
		printf("%u", dirent->inode);
		break;
	case 'n':
		len = dirent->name_len & 0xFF;
		if (len > EXT2_NAME_LEN)
			len = EXT2_NAME_LEN;
		if ((ext2fs_get_rec_len(fs, dirent, &rec_len) == 0) &&
		    (len > rec_len))
			len = rec_len;
		safe_print(dirent->name, len);
		break;
	case 'r':
		(void) ext2fs_get_rec_len(fs, dirent, &rec_len);
		printf("%u", rec_len);
		break;
	case 'l':
		printf("%u", dirent->name_len & 0xFF);
		break;
	case 't':
		printf("%u", dirent->name_len >> 8);
		break;
	default:
	no_dirent:
		printf("%%D%c", ch);
		break;
	}
}
void CrashHandler::CrashSignalHandler( int signal, siginfo_t *si, const ucontext_t *uc )
{
	static volatile bool bInCrashSignalHandler = false;
	if( bInCrashSignalHandler )
	{
		safe_print( 2, "Fatal: crash from within the crash signal handler\n", NULL );
		_exit(1);
	}

	bInCrashSignalHandler = true;

	/* Work around a gcc bug: it reorders the above assignment past other work down
	 * here, even if we declare it volatile.  This makes us not catch recursive
	 * crashes. */
	asm volatile("nop");

	CrashData crash;
	memset( &crash, 0, sizeof(crash) );

	crash.type = CrashData::SIGNAL;
	crash.signal = signal;
	crash.si = *si;

	BacktraceContext ctx;
	GetSignalBacktraceContext( &ctx, uc );
	GetBacktrace( crash.BacktracePointers[0], BACKTRACE_MAX_SIZE, &ctx );
#if defined(HAVE_DECL_SIGUSR1) && HAVE_DECL_SIGUSR1
	if( signal == SIGUSR1 )
		BacktraceAllThreads( crash );
#endif

	strncpy( crash.m_ThreadName[0], RageThread::GetCurrentThreadName(), sizeof(crash.m_ThreadName[0])-1 );

	bInCrashSignalHandler = false;

	/* RunCrashHandler handles any recursive crashes of its own by itself. */
	RunCrashHandler( &crash );
}
Exemplo n.º 16
0
/*
 * This function expands '%dX' expressions
 */
static _INLINE_ void expand_dirent_expression(char ch,
					      struct problem_context *ctx)
{
	struct ext2_dir_entry	*dirent;
	int	len;
	
	if (!ctx || !ctx->dirent)
		goto no_dirent;
	
	dirent = ctx->dirent;
	
	switch (ch) {
	case 'i':
		printf("%u", dirent->inode);
		break;
	case 'n':
		len = dirent->name_len & 0xFF;
		if (len > EXT2_NAME_LEN)
			len = EXT2_NAME_LEN;
		if (len > dirent->rec_len)
			len = dirent->rec_len;
		safe_print(dirent->name, len);
		break;
	case 'r':
		printf("%u", dirent->rec_len);
		break;
	case 'l':
		printf("%u", dirent->name_len & 0xFF);
		break;
	case 't':
		printf("%u", dirent->name_len >> 8);
		break;
	default:
	no_dirent:
		printf("%%D%c", ch);
		break;
	}
}
Exemplo n.º 17
0
/*
 * This function expands '%dX' expressions
 */
static _INLINE_ void expand_dirent_expression(FILE *f, ext2_filsys fs, char ch,
					      struct problem_context *ctx)
{
	struct ext2_dir_entry	*dirent;
	unsigned int rec_len, len;

	if (!ctx || !ctx->dirent)
		goto no_dirent;

	dirent = ctx->dirent;

	switch (ch) {
	case 'i':
		fprintf(f, "%u", dirent->inode);
		break;
	case 'n':
		len = ext2fs_dirent_name_len(dirent);
		if ((ext2fs_get_rec_len(fs, dirent, &rec_len) == 0) &&
		    (len > rec_len))
			len = rec_len;
		safe_print(f, dirent->name, len);
		break;
	case 'r':
		(void) ext2fs_get_rec_len(fs, dirent, &rec_len);
		fprintf(f, "%u", rec_len);
		break;
	case 'l':
		fprintf(f, "%u", ext2fs_dirent_name_len(dirent));
		break;
	case 't':
		fprintf(f, "%u", ext2fs_dirent_file_type(dirent));
		break;
	default:
	no_dirent:
		fprintf(f, "%%D%c", ch);
		break;
	}
}
Exemplo n.º 18
0
static void irc_handle(void) {
  char line[BUFLEN];
  char msg[BUFLEN];
  char *nick;
  char *endline;
  char *p;

  if(get_line(irc_fd, line, BUFLEN) == -1) irc_disconnect();
  if((endline = strpbrk(line, "\r\n"))) *endline = '\0';

  if(verbose > IRC_MSG) safe_print('<', line);

  recv_time = time(NULL);

  if(strncmp(line, "PING ", 5) == 0) {
    line[1] = 'O';/* PING -> PONG */
    irc_write(irc_fd, line);
  }

  p = strchr(line, ' ');
  if(p && strncmp(p, " PRIVMSG ", 9) == 0) {
    *endline = '\n';
    *(endline + 1) = '\0';
    if((p = strchr(p, ':'))) {
      write(program_fd, p + 1, strlen(p + 1));
    }

    /* handle ctcp version */
    if(strcmp(p, ":\x01VERSION\x01\n") == 0) {
      nick = line + 1;/* skip the leading colon */
      if((p = strchr(line, '!'))) *p = '\0';/* lose everything after the nick */
      snprintf(msg, BUFLEN, "NOTICE %s :\x01VERSION fifoirc\x01", nick);
      irc_write(irc_fd, msg);
    }
  }
}
Exemplo n.º 19
0
static void
printlink(FTSENT *p)
{
	int lnklen;
	char name[MAXPATHLEN + 1], path[MAXPATHLEN + 1];

	if (p->fts_level == FTS_ROOTLEVEL)
		(void)snprintf(name, sizeof(name), "%s", p->fts_name);
	else
		(void)snprintf(name, sizeof(name),
		    "%s/%s", p->fts_parent->fts_accpath, p->fts_name);
	if ((lnklen = readlink(name, path, sizeof(path) - 1)) == -1) {
		(void)fprintf(stderr, "\nls: %s: %s\n", name, strerror(errno));
		return;
	}
	path[lnklen] = '\0';
	(void)printf(" -> ");
	if (f_octal || f_octal_escape)
		(void)safe_print(path);
	else if (f_nonprint)
		(void)printescaped(path);
	else
		(void)printf("%s", path);
}
Exemplo n.º 20
0
/** Handler for SIGILL (illegal instruction). */
void ill_handler(int sig, siginfo_t* info, void*) {
#ifdef CVC4_DEBUG
  safe_print(STDERR_FILENO,
             "CVC4 executed an illegal instruction in DEBUG mode.\n");
  if(!segvSpin) {
    print_statistics();
    abort();
  } else {
    safe_print(STDERR_FILENO,
               "Spinning so that a debugger can be connected.\n");
    safe_print(STDERR_FILENO, "Try:  gdb ");
    safe_print(STDERR_FILENO, *progName);
    safe_print(STDERR_FILENO, " ");
    safe_print<int64_t>(STDERR_FILENO, getpid());
    safe_print(STDERR_FILENO, "\n");
    safe_print(STDERR_FILENO, " or:  gdb --pid=");
    safe_print<int64_t>(STDERR_FILENO, getpid());
    safe_print(STDERR_FILENO, " ");
    safe_print(STDERR_FILENO, *progName);
    safe_print(STDERR_FILENO, "\n");
    for(;;) {
      sleep(60);
    }
  }
#else /* CVC4_DEBUG */
  safe_print(STDERR_FILENO, "CVC4 executed an illegal instruction.\n");
  print_statistics();
  abort();
#endif /* CVC4_DEBUG */
}
Exemplo n.º 21
0
void cvc4unexpected() {
#if defined(CVC4_DEBUG) && !defined(__WIN32__)
  safe_print(STDERR_FILENO,
             "\n"
             "CVC4 threw an \"unexpected\" exception (one that wasn't properly "
             "specified\nin the throws() specifier for the throwing function)."
             "\n\n");

  const char* lastContents = LastExceptionBuffer::currentContents();

  if(lastContents == NULL) {
    safe_print(
        STDERR_FILENO,
        "The exception is unknown (maybe it's not a CVC4::Exception).\n\n");
  } else {
    safe_print(STDERR_FILENO, "The exception is:\n");
    safe_print(STDERR_FILENO, lastContents);
    safe_print(STDERR_FILENO, "\n\n");
  }
  if(!segvSpin) {
    print_statistics();
    set_terminate(default_terminator);
  } else {
    safe_print(STDERR_FILENO,
               "Spinning so that a debugger can be connected.\n");
    safe_print(STDERR_FILENO, "Try:  gdb ");
    safe_print(STDERR_FILENO, *progName);
    safe_print(STDERR_FILENO, " ");
    safe_print<int64_t>(STDERR_FILENO, getpid());
    safe_print(STDERR_FILENO, "\n");
    safe_print(STDERR_FILENO, " or:  gdb --pid=");
    safe_print<int64_t>(STDERR_FILENO, getpid());
    safe_print(STDERR_FILENO, " ");
    safe_print(STDERR_FILENO, *progName);
    safe_print(STDERR_FILENO, "\n");
    for(;;) {
      sleep(60);
    }
  }
#else /* CVC4_DEBUG */
  safe_print(STDERR_FILENO, "CVC4 threw an \"unexpected\" exception.\n");
  print_statistics();
  set_terminate(default_terminator);
#endif /* CVC4_DEBUG */
}
Exemplo n.º 22
0
void
printlong(DISPLAY *dp)
{
	struct stat *sp;
	FTSENT *p;
	NAMES *np;
	char buf[20], szbuf[5];

	now = time(NULL);

	printtotal(dp);		/* "total: %u\n" */
	
	for (p = dp->list; p; p = p->fts_link) {
		if (IS_NOPRINT(p))
			continue;
		sp = p->fts_statp;
		if (f_inode)
			(void)printf("%*lu ", dp->s_inode,
			    (unsigned long)sp->st_ino);
		if (f_size) {
			if (f_humanize) {
				if ((humanize_number(szbuf, sizeof(szbuf),
					sp->st_blocks * S_BLKSIZE,
			    "", HN_AUTOSCALE,
			    (HN_DECIMAL | HN_B | HN_NOSPACE))) == -1)
				err(1, "humanize_number");
			(void)printf("%*s ", dp->s_block, szbuf);
			} else {
			(void)printf("%*llu ", dp->s_block,
					(long long)howmany(sp->st_blocks,
							   	blocksize));
			}
		}
		(void)strmode(sp->st_mode, buf);
		np = p->fts_pointer;
		(void)printf("%s %*lu ", buf, dp->s_nlink,
		    (unsigned long)sp->st_nlink);
		if (!f_grouponly)
			(void)printf("%-*s  ", dp->s_user, np->user);
		(void)printf("%-*s  ", dp->s_group, np->group);
		if (f_flags)
			(void)printf("%-*s ", dp->s_flags, np->flags);
		if (S_ISCHR(sp->st_mode) || S_ISBLK(sp->st_mode))
			(void)printf("%*u, %*u ",
			    dp->s_major, major(sp->st_rdev), dp->s_minor,
			    minor(sp->st_rdev));
		else
			if (f_humanize) {
				if ((humanize_number(szbuf, sizeof(szbuf),
				    sp->st_size, "", HN_AUTOSCALE,
				    (HN_DECIMAL | HN_B | HN_NOSPACE))) == -1)
					err(1, "humanize_number");
				(void)printf("%*s ", dp->s_size, szbuf);
			} else {
				(void)printf("%*llu ", dp->s_size,
				    (long long)sp->st_size);
			}
		if (f_accesstime)
			printtime(sp->st_atime);
		else if (f_statustime)
			printtime(sp->st_ctime);
		else
			printtime(sp->st_mtime);
		if (f_octal || f_octal_escape)
			(void)safe_print(p->fts_name);
		else if (f_nonprint)
			(void)printescaped(p->fts_name);
		else
			(void)printf("%s", p->fts_name);

		if (f_type || (f_typedir && S_ISDIR(sp->st_mode)))
			(void)printtype(sp->st_mode);
		if (S_ISLNK(sp->st_mode))
			printlink(p);
		(void)putchar('\n');
	}
}
Exemplo n.º 23
0
/** Handler for SIGINT, i.e., when the user hits control C. */
void sigint_handler(int sig, siginfo_t* info, void*) {
  safe_print(STDERR_FILENO, "CVC4 interrupted by user.\n");
  print_statistics();
  abort();
}
Exemplo n.º 24
0
int
append(void)
{
	ARCHD *arcn;
	int res;
	FSUB *orgfrmt;
	int udev;
	off_t tlen;

	arcn = &archd;
	orgfrmt = frmt;

	/*
	 * Do not allow an append operation if the actual archive is of a
	 * different format than the user specified format.
	 */
	if (get_arc() < 0)
		return 1;
	if ((orgfrmt != NULL) && (orgfrmt != frmt)) {
		tty_warn(1, "Cannot mix current archive format %s with %s",
		    frmt->name, orgfrmt->name);
		return 1;
	}

	/*
	 * pass the format any options and start up format
	 */
	if (((*frmt->options)() < 0) || ((*frmt->st_rd)() < 0))
		return 1;

	/*
	 * if we only are adding members that are newer, we need to save the
	 * mod times for all files we see.
	 */
	if (uflag && (ftime_start() < 0))
		return 1;

	/*
	 * some archive formats encode hard links by recording the device and
	 * file serial number (inode) but copy the file anyway (multiple times)
	 * to the archive. When we append, we run the risk that newly added
	 * files may have the same device and inode numbers as those recorded
	 * on the archive but during a previous run. If this happens, when the
	 * archive is extracted we get INCORRECT hard links. We avoid this by
	 * remapping the device numbers so that newly added files will never
	 * use the same device number as one found on the archive. remapping
	 * allows new members to safely have links among themselves. remapping
	 * also avoids problems with file inode (serial number) truncations
	 * when the inode number is larger than storage space in the archive
	 * header. See the remap routines for more details.
	 */
	if ((udev = frmt->udev) && (dev_start() < 0))
		return 1;

	/*
	 * reading the archive may take a long time. If verbose tell the user
	 */
	if (vflag || Vflag) {
		(void)fprintf(listf,
			"%s: Reading archive to position at the end...", argv0);
		vfpart = 1;
	}

	/*
	 * step through the archive until the format says it is done
	 */
	while (next_head(arcn) == 0) {
		/*
		 * check if this file meets user specified options.
		 */
		if (sel_chk(arcn) != 0) {
			if (rd_skip(arcn->skip + arcn->pad) == 1)
				break;
			continue;
		}

		if (uflag) {
			/*
			 * see if this is the newest version of this file has
			 * already been seen, if so skip.
			 */
			if ((res = chk_ftime(arcn)) < 0)
				break;
			if (res > 0) {
				if (rd_skip(arcn->skip + arcn->pad) == 1)
					break;
				continue;
			}
		}

		/*
		 * Store this device number. Device numbers seen during the
		 * read phase of append will cause newly appended files with a
		 * device number seen in the old part of the archive to be
		 * remapped to an unused device number.
		 */
		if ((udev && (add_dev(arcn) < 0)) ||
		    (rd_skip(arcn->skip + arcn->pad) == 1))
			break;
	}

	/*
	 * done, finish up read and get the number of bytes to back up so we
	 * can add new members. The format might have used the hard link table,
	 * purge it.
	 */
	tlen = (*frmt->end_rd)();
	lnk_end();

	/*
	 * try to position for write, if this fails quit. if any error occurs,
	 * we will refuse to write
	 */
	if (appnd_start(tlen) < 0)
		return 1;

	/*
	 * tell the user we are done reading.
	 */
	if ((vflag || Vflag) && vfpart) {
		(void)safe_print("done.\n", listf);
		vfpart = 0;
	}

	/*
	 * go to the writing phase to add the new members
	 */
	res = wr_archive(arcn, 1);
	if (res == 1) {
		/*
		 * wr_archive failed in some way, but before any files were
		 * added. These are the only steps needed to cleanup (and
		 * not truncate the archive).
		 */
		wr_fin();
		(void)sigprocmask(SIG_BLOCK, &s_mask, (sigset_t *)NULL);
		ar_close();
	}
	return res;
}
static void RunCrashHandler( const CrashData *crash )
{
	if( g_pCrashHandlerArgv0 == NULL )
	{
		safe_print( fileno(stderr), "Crash handler failed: CrashHandlerHandleArgs was not called\n", NULL );
		_exit( 1 );
	}
	
	/* Block SIGPIPE, so we get EPIPE. */
	struct sigaction sa;
	memset( &sa, 0, sizeof(sa) );
	sa.sa_handler = SIG_IGN;
	if( sigaction( SIGPIPE, &sa, NULL ) != 0 )
	{
		safe_print( fileno(stderr), "sigaction() failed: %s", strerror(errno), NULL );
		/* non-fatal */
	}

	static int received = 0;
	static int active = 0;

	if( active )
	{
		/* We've received a second signal.  This may mean that another thread
		 * crashed before we stopped it, or it may mean that the crash handler
		 * crashed. */
		switch( crash->type )
		{
		case CrashData::SIGNAL:
			safe_print( fileno(stderr), "Fatal signal (", SignalName(crash->signal), ")", NULL );
			break;

		case CrashData::FORCE_CRASH:
			safe_print( fileno(stderr), "Crash handler failed: \"", crash->reason, "\"", NULL );
			break;

		default:
			safe_print( fileno(stderr), "Unexpected RunCrashHandler call (", itoa(crash->type), ")", NULL );
			break;
		}

		if( active == 1 )
			safe_print( fileno(stderr), " while still in the crash handler\n", NULL);
		else if( active == 2 )
			safe_print( fileno(stderr), " while in the crash handler child\n", NULL);

		_exit( 1 );
	}
	active = 1;
	received = getpid();

	/* Stop other threads.  XXX: This prints a spurious ptrace error if any threads
	 * are already suspended, which happens in ForceCrashHandlerDeadlock(). */
	RageThread::HaltAllThreads();
	
	/* We need to be very careful, since we're under crash conditions.  Let's fork
	 * a process and exec ourself to get a clean environment to work in. */
	int fds[2];
	if( pipe(fds) != 0 )
	{
		safe_print( fileno(stderr), "Crash handler pipe() failed: ", strerror(errno), "\n", NULL );
		exit( 1 );
	}

	pid_t childpid = fork();
	if( childpid == -1 )
	{
		safe_print( fileno(stderr), "Crash handler fork() failed: ", strerror(errno), "\n", NULL );
		_exit( 1 );
	}

	if( childpid == 0 )
	{
		active = 2;
		close( fds[1] );
		spawn_child_process( fds[0] );
	}
	else
	{
		close( fds[0] );
		parent_process( fds[1], crash );
		close( fds[1] );

		int status = 0;
#if !defined(MACOSX)
		waitpid( childpid, &status, 0 );
#endif

		/* We need to resume threads before continuing, or we may deadlock on _exit(). */
		/* XXX: race condition:  If two threads are deadlocked on a pair of mutexes, there's
		 * a chance that they'll both try to lock the other's mutex at the same time.  If
		 * that happens, then they'll both time out the lock at about the same time.  One
		 * will trigger the deadlock crash first, and the other will be suspended.  However,
		 * once we resume it here, it'll continue, and * trigger the deadlock crash again.
		 * It can result in unrecoverable deadlocks. */
		RageThread::ResumeAllThreads();

		if( WIFSIGNALED(status) )
			safe_print( fileno(stderr), "Crash handler child exited with signal ", itoa(WTERMSIG(status)), "\n", NULL );
	}
}
Exemplo n.º 26
0
int
extract(void)
{
	ARCHD *arcn;
	int res;
	off_t cnt;
	struct stat sb;
	int fd;
	time_t now;

	arcn = &archd;
	/*
	 * figure out archive type; pass any format specific options to the
	 * archive option processing routine; call the format init routine;
	 * start up the directory modification time and access mode database
	 */
	if ((get_arc() < 0) || ((*frmt->options)() < 0) ||
	    ((*frmt->st_rd)() < 0) || (dir_start() < 0))
		return 1;

	now = time((time_t *)NULL);
#if !HAVE_NBTOOL_CONFIG_H
	if (do_chroot)
		(void)fdochroot(cwdfd);
#endif

	/*
	 * When we are doing interactive rename, we store the mapping of names
	 * so we can fix up hard links files later in the archive.
	 */
	if (iflag && (name_start() < 0))
		return 1;

	/*
	 * step through each entry on the archive until the format read routine
	 * says it is done
	 */
	while (next_head(arcn) == 0) {
		int write_to_hard_link = 0;

		if (arcn->type == PAX_GLL || arcn->type == PAX_GLF) {
			/*
			 * we need to read, to get the real filename
			 */
			if (!(*frmt->rd_data)(arcn, -arcn->type, &cnt))
				(void)rd_skip(cnt + arcn->pad);
			continue;
		}

		/*
		 * check for pattern, and user specified options match. When
		 * all the patterns are matched we are done
		 */
		if ((res = pat_match(arcn)) < 0)
			break;

		if ((res > 0) || (sel_chk(arcn) != 0)) {
			/*
			 * file is not selected. skip past any file
			 * data and padding and go back for the next
			 * archive member
			 */
			(void)rd_skip(arcn->skip + arcn->pad);
			continue;
		}

		if (kflag && (lstat(arcn->name, &sb) == 0)) {
			(void)rd_skip(arcn->skip + arcn->pad);
			continue;
		}

		/*
		 * with -u or -D only extract when the archive member is newer
		 * than the file with the same name in the file system (no
		 * test of being the same type is required).
		 * NOTE: this test is done BEFORE name modifications as
		 * specified by pax. this operation can be confusing to the
		 * user who might expect the test to be done on an existing
		 * file AFTER the name mod. In honesty the pax spec is probably
		 * flawed in this respect.  ignore this for GNU long links.
		 */
		if ((uflag || Dflag) && ((lstat(arcn->name, &sb) == 0))) {
			if (uflag && Dflag) {
				if ((arcn->sb.st_mtime <= sb.st_mtime) &&
				    (arcn->sb.st_ctime <= sb.st_ctime)) {
					(void)rd_skip(arcn->skip + arcn->pad);
					continue;
				}
			} else if (Dflag) {
				if (arcn->sb.st_ctime <= sb.st_ctime) {
					(void)rd_skip(arcn->skip + arcn->pad);
					continue;
				}
			} else if (arcn->sb.st_mtime <= sb.st_mtime) {
				(void)rd_skip(arcn->skip + arcn->pad);
				continue;
			}
		}

		/*
		 * this archive member is now been selected. modify the name.
		 */
		if ((pat_sel(arcn) < 0) || ((res = mod_name(arcn, RENM)) < 0))
			break;
		if (res > 0) {
			/*
			 * a bad name mod, skip and purge name from link table
			 */
			purg_lnk(arcn);
			(void)rd_skip(arcn->skip + arcn->pad);
			continue;
		}

		if (arcn->name[0] == '/' && !check_Aflag()) {
			memmove(arcn->name, arcn->name + 1, strlen(arcn->name));
		}
		/*
		 * Non standard -Y and -Z flag. When the existing file is
		 * same age or newer skip; ignore this for GNU long links.
		 */
		if ((Yflag || Zflag) && ((lstat(arcn->name, &sb) == 0))) {
			if (Yflag && Zflag) {
				if ((arcn->sb.st_mtime <= sb.st_mtime) &&
				    (arcn->sb.st_ctime <= sb.st_ctime)) {
					(void)rd_skip(arcn->skip + arcn->pad);
					continue;
				}
			} else if (Yflag) {
				if (arcn->sb.st_ctime <= sb.st_ctime) {
					(void)rd_skip(arcn->skip + arcn->pad);
					continue;
				}
			} else if (arcn->sb.st_mtime <= sb.st_mtime) {
				(void)rd_skip(arcn->skip + arcn->pad);
				continue;
			}
		}

		if (vflag) {
			if (vflag > 1)
				ls_list(arcn, now, listf);
			else {
				(void)safe_print(arcn->name, listf);
				vfpart = 1;
			}
		}

		/*
		 * if required, chdir around.
		 */
		if ((arcn->pat != NULL) && (arcn->pat->chdname != NULL) &&
		    !to_stdout)
			dochdir(arcn->pat->chdname);

		if (secure && path_check(arcn, 0) != 0) {
			(void)rd_skip(arcn->skip + arcn->pad);
			continue;
		}

			
		/*
		 * all ok, extract this member based on type
		 */
		if ((arcn->type != PAX_REG) && (arcn->type != PAX_CTG)) {
			/*
			 * process archive members that are not regular files.
			 * throw out padding and any data that might follow the
			 * header (as determined by the format).
			 */
			if ((arcn->type == PAX_HLK) ||
			    (arcn->type == PAX_HRG))
				res = lnk_creat(arcn, &write_to_hard_link);
			else
				res = node_creat(arcn);

			if (!write_to_hard_link) {
				(void)rd_skip(arcn->skip + arcn->pad);
				if (res < 0)
					purg_lnk(arcn);

				if (vflag && vfpart) {
					(void)putc('\n', listf);
					vfpart = 0;
				}
				continue;
			}
		}
		if (to_stdout)
			fd = STDOUT_FILENO;
		else {
			/*
			 * We have a file with data here. If we cannot create
			 * it, skip over the data and purge the name from hard
			 * link table.
			 */
			if ((fd = file_creat(arcn, write_to_hard_link)) < 0) {
				(void)fflush(listf);
				(void)rd_skip(arcn->skip + arcn->pad);
				purg_lnk(arcn);
				continue;
			}
		}
		/*
		 * extract the file from the archive and skip over padding and
		 * any unprocessed data
		 */
		res = (*frmt->rd_data)(arcn, fd, &cnt);
		if (!to_stdout)
			file_close(arcn, fd);
		if (vflag && vfpart) {
			(void)putc('\n', listf);
			vfpart = 0;
		}
		if (!res)
			(void)rd_skip(cnt + arcn->pad);

		/*
		 * if required, chdir around.
		 */
		if ((arcn->pat != NULL) && (arcn->pat->chdname != NULL))
			fdochdir(cwdfd);
	}

	/*
	 * all done, restore directory modes and times as required; make sure
	 * all patterns supplied by the user were matched; block off signals
	 * to avoid chance for multiple entry into the cleanup code.
	 */
	(void)(*frmt->end_rd)();
	(void)sigprocmask(SIG_BLOCK, &s_mask, (sigset_t *)NULL);
	ar_close();
	proc_dir();
	pat_chk();

	return 0;
}
Exemplo n.º 27
0
static int
wr_archive(ARCHD *arcn, int is_app)
{
	int res;
	int hlk;
	int wr_one;
	off_t cnt;
	int (*wrf)(ARCHD *);
	int fd = -1;
	time_t now;

	/*
	 * if this format supports hard link storage, start up the database
	 * that detects them.
	 */
	if (((hlk = frmt->hlk) == 1) && (lnk_start() < 0))
		return 1;

	/*
	 * start up the file traversal code and format specific write
	 */
	if ((ftree_start() < 0) || ((*frmt->st_wr)() < 0))
		return 1;
	wrf = frmt->wr;

	now = time((time_t *)NULL);

	/*
	 * When we are doing interactive rename, we store the mapping of names
	 * so we can fix up hard links files later in the archive.
	 */
	if (iflag && (name_start() < 0))
		return 1;

	/*
	 * if this is not append, and there are no files, we do no write a trailer
	 */
	wr_one = is_app;

	/*
	 * while there are files to archive, process them one at at time
	 */
	while (next_file(arcn) == 0) {
		/*
		 * check if this file meets user specified options match.
		 */
		if (sel_chk(arcn) != 0)
			continue;
		/*
		 * Here we handle the exclusion -X gnu style patterns which
		 * are implemented like a pattern list. We don't modify the
		 * name as this will be done below again, and we don't want
		 * to double modify it.
		 */
		if ((res = mod_name(arcn, 0)) < 0)
			break;
		if (res == 1)
			continue;
		fd = -1;
		if (uflag) {
			/*
			 * only archive if this file is newer than a file with
			 * the same name that is already stored on the archive
			 */
			if ((res = chk_ftime(arcn)) < 0)
				break;
			if (res > 0)
				continue;
		}

		/*
		 * this file is considered selected now. see if this is a hard
		 * link to a file already stored
		 */
		ftree_sel(arcn);
		if (hlk && (chk_lnk(arcn) < 0))
			break;

		if ((arcn->type == PAX_REG) || (arcn->type == PAX_HRG) ||
		    (arcn->type == PAX_CTG)) {
			/*
			 * we will have to read this file. by opening it now we
			 * can avoid writing a header to the archive for a file
			 * we were later unable to read (we also purge it from
			 * the link table).
			 */
			if ((fd = open(arcn->org_name, O_RDONLY, 0)) < 0) {
				syswarn(1, errno, "Unable to open %s to read",
					arcn->org_name);
				purg_lnk(arcn);
				continue;
			}
		}

		/*
		 * Now modify the name as requested by the user
		 */
		if ((res = mod_name(arcn, RENM)) < 0) {
			/*
			 * name modification says to skip this file, close the
			 * file and purge link table entry
			 */
			rdfile_close(arcn, &fd);
			purg_lnk(arcn);
			break;
		}

		if (arcn->name[0] == '/' && !check_Aflag()) {
			memmove(arcn->name, arcn->name + 1, strlen(arcn->name));
		}

		if ((res > 0) || (docrc && (set_crc(arcn, fd) < 0))) {
			/*
			 * unable to obtain the crc we need, close the file,
			 * purge link table entry
			 */
			rdfile_close(arcn, &fd);
			purg_lnk(arcn);
			continue;
		}

		if (vflag) {
			if (vflag > 1)
				ls_list(arcn, now, listf);
			else {
				(void)safe_print(arcn->name, listf);
				vfpart = 1;
			}
		}
		++flcnt;

		/*
		 * looks safe to store the file, have the format specific
		 * routine write routine store the file header on the archive
		 */
		if ((res = (*wrf)(arcn)) < 0) {
			rdfile_close(arcn, &fd);
			break;
		}
		wr_one = 1;
		if (res > 0) {
			/*
			 * format write says no file data needs to be stored
			 * so we are done messing with this file
			 */
			if (vflag && vfpart) {
				(void)putc('\n', listf);
				vfpart = 0;
			}
			rdfile_close(arcn, &fd);
			continue;
		}

		/*
		 * Add file data to the archive, quit on write error. if we
		 * cannot write the entire file contents to the archive we
		 * must pad the archive to replace the missing file data
		 * (otherwise during an extract the file header for the file
		 * which FOLLOWS this one will not be where we expect it to
		 * be).
		 */
		res = (*frmt->wr_data)(arcn, fd, &cnt);
		rdfile_close(arcn, &fd);
		if (vflag && vfpart) {
			(void)putc('\n', listf);
			vfpart = 0;
		}
		if (res < 0)
			break;

		/*
		 * pad as required, cnt is number of bytes not written
		 */
		if (((cnt > 0) && (wr_skip(cnt) < 0)) ||
		    ((arcn->pad > 0) && (wr_skip(arcn->pad) < 0)))
			break;
	}

	/*
	 * tell format to write trailer; pad to block boundary; reset directory
	 * mode/access times, and check if all patterns supplied by the user
	 * were matched. block off signals to avoid chance for multiple entry
	 * into the cleanup code
	 */
	if (wr_one) {
		(*frmt->end_wr)();
		wr_fin();
	}
	(void)sigprocmask(SIG_BLOCK, &s_mask, (sigset_t *)NULL);
	ar_close();
	if (tflag)
		proc_dir();
	ftree_chk();

	return 0;
}
Exemplo n.º 28
0
/** Handler for SIGSEGV (segfault). */
void segv_handler(int sig, siginfo_t* info, void* c) {
  uintptr_t extent = reinterpret_cast<uintptr_t>(cvc4StackBase) - cvc4StackSize;
  uintptr_t addr = reinterpret_cast<uintptr_t>(info->si_addr);
#ifdef CVC4_DEBUG
  safe_print(STDERR_FILENO, "CVC4 suffered a segfault in DEBUG mode.\n");
  safe_print(STDERR_FILENO, "Offending address is ");
  safe_print(STDERR_FILENO, info->si_addr);
  safe_print(STDERR_FILENO, "\n");
  //cerr << "base is " << (void*)cvc4StackBase << endl;
  //cerr << "size is " << cvc4StackSize << endl;
  //cerr << "extent is " << (void*)extent << endl;
  if(addr >= extent && addr <= extent + 10*1024) {
    safe_print(STDERR_FILENO,
               "Looks like this is likely due to stack overflow.\n");
    safe_print(STDERR_FILENO,
               "You might consider increasing the limit with `ulimit -s' or "
               "equivalent.\n");
  } else if(addr < 10*1024) {
    safe_print(STDERR_FILENO, "Looks like a NULL pointer was dereferenced.\n");
  }

  if(!segvSpin) {
    print_statistics();
    abort();
  } else {
    safe_print(STDERR_FILENO,
               "Spinning so that a debugger can be connected.\n");
    safe_print(STDERR_FILENO, "Try:  gdb ");
    safe_print(STDERR_FILENO, *progName);
    safe_print(STDERR_FILENO, " ");
    safe_print<int64_t>(STDERR_FILENO, getpid());
    safe_print(STDERR_FILENO, "\n");
    safe_print(STDERR_FILENO, " or:  gdb --pid=");
    safe_print<int64_t>(STDERR_FILENO, getpid());
    safe_print(STDERR_FILENO, " ");
    safe_print(STDERR_FILENO, *progName);
    safe_print(STDERR_FILENO, "\n");
    for(;;) {
      sleep(60);
    }
  }
#else /* CVC4_DEBUG */
  safe_print(STDERR_FILENO, "CVC4 suffered a segfault.\n");
  safe_print(STDERR_FILENO, "Offending address is ");
  safe_print(STDERR_FILENO, info->si_addr);
  safe_print(STDERR_FILENO, "\n");
  if(addr >= extent && addr <= extent + 10*1024) {
    safe_print(STDERR_FILENO,
               "Looks like this is likely due to stack overflow.\n");
    safe_print(STDERR_FILENO,
               "You might consider increasing the limit with `ulimit -s' or "
               "equivalent.\n");
  } else if(addr < 10*1024) {
    safe_print(STDERR_FILENO, "Looks like a NULL pointer was dereferenced.\n");
  }
  print_statistics();
  abort();
#endif /* CVC4_DEBUG */
}
Exemplo n.º 29
0
int
copy(void)
{
	ARCHD *arcn;
	int res;
	int fddest;
	char *dest_pt;
	int dlen;
	int drem;
	int fdsrc = -1;
	struct stat sb;
	char dirbuf[PAXPATHLEN+1];

	arcn = &archd;
	/*
	 * set up the destination dir path and make sure it is a directory. We
	 * make sure we have a trailing / on the destination
	 */
	dlen = strlcpy(dirbuf, dirptr, sizeof(dirbuf));
	if (dlen >= sizeof(dirbuf) ||
	    (dlen == sizeof(dirbuf) - 1 && dirbuf[dlen - 1] != '/')) {
		tty_warn(1, "directory name is too long %s", dirptr);
		return 1;
	}
	dest_pt = dirbuf + dlen;
	if (*(dest_pt-1) != '/') {
		*dest_pt++ = '/';
		++dlen;
	}
	*dest_pt = '\0';
	drem = PAXPATHLEN - dlen;

	if (stat(dirptr, &sb) < 0) {
		syswarn(1, errno, "Cannot access destination directory %s",
			dirptr);
		return 1;
	}
	if (!S_ISDIR(sb.st_mode)) {
		tty_warn(1, "Destination is not a directory %s", dirptr);
		return 1;
	}

	/*
	 * start up the hard link table; file traversal routines and the
	 * modification time and access mode database
	 */
	if ((lnk_start() < 0) || (ftree_start() < 0) || (dir_start() < 0))
		return 1;

	/*
	 * When we are doing interactive rename, we store the mapping of names
	 * so we can fix up hard links files later in the archive.
	 */
	if (iflag && (name_start() < 0))
		return 1;

	/*
	 * set up to cp file trees
	 */
	cp_start();

	/*
	 * while there are files to archive, process them
	 */
	while (next_file(arcn) == 0) {
		fdsrc = -1;

		/*
		 * check if this file meets user specified options
		 */
		if (sel_chk(arcn) != 0)
			continue;

		/*
		 * if there is already a file in the destination directory with
		 * the same name and it is newer, skip the one stored on the
		 * archive.
		 * NOTE: this test is done BEFORE name modifications as
		 * specified by pax. this can be confusing to the user who
		 * might expect the test to be done on an existing file AFTER
		 * the name mod. In honesty the pax spec is probably flawed in
		 * this respect
		 */
		if (uflag || Dflag) {
			/*
			 * create the destination name
			 */
			if (strlcpy(dest_pt, arcn->name + (*arcn->name == '/'),
			    drem + 1) > drem) {
				tty_warn(1, "Destination pathname too long %s",
					arcn->name);
				continue;
			}

			/*
			 * if existing file is same age or newer skip
			 */
			res = lstat(dirbuf, &sb);
			*dest_pt = '\0';

			if (res == 0) {
				if (uflag && Dflag) {
					if ((arcn->sb.st_mtime<=sb.st_mtime) &&
					    (arcn->sb.st_ctime<=sb.st_ctime))
						continue;
				} else if (Dflag) {
					if (arcn->sb.st_ctime <= sb.st_ctime)
						continue;
				} else if (arcn->sb.st_mtime <= sb.st_mtime)
					continue;
			}
		}

		/*
		 * this file is considered selected. See if this is a hard link
		 * to a previous file; modify the name as requested by the
		 * user; set the final destination.
		 */
		ftree_sel(arcn);
		if ((chk_lnk(arcn) < 0) || ((res = mod_name(arcn, RENM)) < 0))
			break;
		if ((res > 0) || (set_dest(arcn, dirbuf, dlen) < 0)) {
			/*
			 * skip file, purge from link table
			 */
			purg_lnk(arcn);
			continue;
		}

		/*
		 * Non standard -Y and -Z flag. When the exisiting file is
		 * same age or newer skip
		 */
		if ((Yflag || Zflag) && ((lstat(arcn->name, &sb) == 0))) {
			if (Yflag && Zflag) {
				if ((arcn->sb.st_mtime <= sb.st_mtime) &&
				    (arcn->sb.st_ctime <= sb.st_ctime))
					continue;
			} else if (Yflag) {
				if (arcn->sb.st_ctime <= sb.st_ctime)
					continue;
			} else if (arcn->sb.st_mtime <= sb.st_mtime)
				continue;
		}

		if (vflag) {
			(void)safe_print(arcn->name, listf);
			vfpart = 1;
		}
		++flcnt;

		/*
		 * try to create a hard link to the src file if requested
		 * but make sure we are not trying to overwrite ourselves.
		 */
		if (lflag)
			res = cross_lnk(arcn);
		else
			res = chk_same(arcn);
		if (res <= 0) {
			if (vflag && vfpart) {
				(void)putc('\n', listf);
				vfpart = 0;
			}
			continue;
		}

		/*
		 * have to create a new file
		 */
		if ((arcn->type != PAX_REG) && (arcn->type != PAX_CTG)) {
			/*
			 * create a link or special file
			 */
			if ((arcn->type == PAX_HLK) ||
			    (arcn->type == PAX_HRG)) {
				int payload;

				res = lnk_creat(arcn, &payload);
			} else {
				res = node_creat(arcn);
			}
			if (res < 0)
				purg_lnk(arcn);
			if (vflag && vfpart) {
				(void)putc('\n', listf);
				vfpart = 0;
			}
			continue;
		}

		/*
		 * have to copy a regular file to the destination directory.
		 * first open source file and then create the destination file
		 */
		if ((fdsrc = open(arcn->org_name, O_RDONLY, 0)) < 0) {
			syswarn(1, errno, "Unable to open %s to read",
			    arcn->org_name);
			purg_lnk(arcn);
			continue;
		}
		if ((fddest = file_creat(arcn, 0)) < 0) {
			rdfile_close(arcn, &fdsrc);
			purg_lnk(arcn);
			continue;
		}

		/*
		 * copy source file data to the destination file
		 */
		cp_file(arcn, fdsrc, fddest);
		file_close(arcn, fddest);
		rdfile_close(arcn, &fdsrc);

		if (vflag && vfpart) {
			(void)putc('\n', listf);
			vfpart = 0;
		}
	}

	/*
	 * restore directory modes and times as required; make sure all
	 * patterns were selected block off signals to avoid chance for
	 * multiple entry into the cleanup code.
	 */
	(void)sigprocmask(SIG_BLOCK, &s_mask, (sigset_t *)NULL);
	ar_close();
	proc_dir();
	ftree_chk();

	return 0;
}